make FailType a PlayerOption instead of a SongOption; fixes
peculiarity that GameState::GetPlayerFailType can implement fail modes per-player and nothing else can
This commit is contained in:
@@ -866,7 +866,7 @@ bool BackgroundImpl::IsDangerAllVisible()
|
||||
{
|
||||
/* The players are never in danger in FAIL_OFF. */
|
||||
FOREACH_PlayerNumber( p )
|
||||
if( GAMESTATE->GetPlayerFailType(GAMESTATE->m_pPlayerState[p]) == SongOptions::FAIL_OFF )
|
||||
if( GAMESTATE->GetPlayerFailType(GAMESTATE->m_pPlayerState[p]) == PlayerOptions::FAIL_OFF )
|
||||
return false;
|
||||
if( !g_bShowDanger )
|
||||
return false;
|
||||
|
||||
@@ -1294,10 +1294,10 @@ void setmax( T &a, const T &b )
|
||||
a = max(a, b);
|
||||
}
|
||||
|
||||
SongOptions::FailType GameState::GetPlayerFailType( const PlayerState *pPlayerState ) const
|
||||
PlayerOptions::FailType GameState::GetPlayerFailType( const PlayerState *pPlayerState ) const
|
||||
{
|
||||
PlayerNumber pn = pPlayerState->m_PlayerNumber;
|
||||
SongOptions::FailType ft = m_SongOptions.GetCurrent().m_FailType;
|
||||
PlayerOptions::FailType ft = pPlayerState->m_PlayerOptions.GetCurrent().m_FailType;
|
||||
|
||||
/* If the player changed the fail mode explicitly, leave it alone. */
|
||||
if( m_bChangedFailTypeOnScreenSongOptions )
|
||||
@@ -1306,7 +1306,7 @@ SongOptions::FailType GameState::GetPlayerFailType( const PlayerState *pPlayerSt
|
||||
if( IsCourseMode() )
|
||||
{
|
||||
if( PREFSMAN->m_bMinimum1FullSongInCourses && GetCourseSongIndex()==0 )
|
||||
ft = max( ft, SongOptions::FAIL_IMMEDIATE_CONTINUE ); // take the least harsh of the two FailTypes
|
||||
ft = max( ft, PlayerOptions::FAIL_IMMEDIATE_CONTINUE ); // take the least harsh of the two FailTypes
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -1323,18 +1323,18 @@ SongOptions::FailType GameState::GetPlayerFailType( const PlayerState *pPlayerSt
|
||||
|
||||
/* Easy and beginner are never harder than FAIL_IMMEDIATE_CONTINUE. */
|
||||
if( dc <= Difficulty_Easy )
|
||||
setmax( ft, SongOptions::FAIL_IMMEDIATE_CONTINUE );
|
||||
setmax( ft, PlayerOptions::FAIL_IMMEDIATE_CONTINUE );
|
||||
|
||||
if( dc <= Difficulty_Easy && bFirstStageForAny && PREFSMAN->m_bFailOffForFirstStageEasy )
|
||||
setmax( ft, SongOptions::FAIL_OFF );
|
||||
setmax( ft, PlayerOptions::FAIL_OFF );
|
||||
|
||||
/* If beginner's steps were chosen, and this is the first stage,
|
||||
* turn off failure completely. */
|
||||
if( dc == Difficulty_Beginner && bFirstStageForAny )
|
||||
setmax( ft, SongOptions::FAIL_OFF );
|
||||
setmax( ft, PlayerOptions::FAIL_OFF );
|
||||
|
||||
if( dc == Difficulty_Beginner && PREFSMAN->m_bFailOffInBeginner )
|
||||
setmax( ft, SongOptions::FAIL_OFF );
|
||||
setmax( ft, PlayerOptions::FAIL_OFF );
|
||||
}
|
||||
|
||||
return ft;
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
#include "MessageManager.h"
|
||||
#include "ModsGroup.h"
|
||||
#include "RageTimer.h"
|
||||
#include "PlayerOptions.h"
|
||||
#include "SongOptions.h"
|
||||
|
||||
#include <map>
|
||||
@@ -237,7 +238,7 @@ public:
|
||||
bool CurrentOptionsDisqualifyPlayer( PlayerNumber pn );
|
||||
bool PlayerIsUsingModifier( PlayerNumber pn, const RString &sModifier );
|
||||
|
||||
SongOptions::FailType GetPlayerFailType( const PlayerState *pPlayerState ) const;
|
||||
PlayerOptions::FailType GetPlayerFailType( const PlayerState *pPlayerState ) const;
|
||||
|
||||
// character stuff
|
||||
Character* m_pCurCharacters[NUM_PLAYERS];
|
||||
|
||||
@@ -37,6 +37,7 @@ void PlayerOptions::Init()
|
||||
ZERO( m_bTurns );
|
||||
ZERO( m_bTransforms );
|
||||
m_bMuteOnError = false;
|
||||
m_FailType = FAIL_IMMEDIATE;
|
||||
m_ScoreDisplay = SCORING_ADD;
|
||||
m_sNoteSkin = "";
|
||||
}
|
||||
@@ -180,6 +181,15 @@ void PlayerOptions::GetMods( vector<RString> &AddTo, bool bForceNoteSkin ) const
|
||||
if( m_bTransforms[TRANSFORM_NOSTRETCH] )AddTo.push_back( "NoStretch" );
|
||||
if( m_bMuteOnError ) AddTo.push_back( "MuteOnError" );
|
||||
|
||||
switch( m_FailType )
|
||||
{
|
||||
case FAIL_IMMEDIATE: break;
|
||||
case FAIL_IMMEDIATE_CONTINUE: AddTo.push_back("FailImmediateContinue"); break;
|
||||
case FAIL_AT_END: AddTo.push_back("FailAtEnd"); break;
|
||||
case FAIL_OFF: AddTo.push_back("FailOff"); break;
|
||||
default: ASSERT(0);
|
||||
}
|
||||
|
||||
if( m_fSkew==0 && m_fPerspectiveTilt==0 ) { if( m_bSetTiltOrSkew ) AddTo.push_back( "Overhead" ); }
|
||||
else if( m_fSkew == 0 )
|
||||
{
|
||||
@@ -354,6 +364,18 @@ void PlayerOptions::FromString( const RString &sOptions, bool bWarnOnInvalid )
|
||||
else if( NOTESKIN && NOTESKIN->DoesNoteSkinExist(sBit) ) m_sNoteSkin = sBit;
|
||||
else if( sBit == "noteskin" && !on ) /* "no noteskin" */ m_sNoteSkin = CommonMetrics::DEFAULT_NOTESKIN_NAME;
|
||||
else if( sBit == "randomspeed" ) SET_FLOAT( fRandomSpeed )
|
||||
else if( sBit == "failarcade" ||
|
||||
sBit == "failimmediate" ) m_FailType = FAIL_IMMEDIATE;
|
||||
else if( sBit == "failendofsong" ||
|
||||
sBit == "failimmediatecontinue" ) m_FailType = FAIL_IMMEDIATE_CONTINUE;
|
||||
else if( sBit == "failatend" ) m_FailType = FAIL_AT_END;
|
||||
else if( sBit == "failoff" ) m_FailType = FAIL_OFF;
|
||||
else if( sBit == "faildefault" )
|
||||
{
|
||||
PlayerOptions po;
|
||||
GAMESTATE->GetDefaultPlayerOptions( po );
|
||||
m_FailType = po.m_FailType;
|
||||
}
|
||||
else if( sBit == "addscore" ) m_ScoreDisplay = SCORING_ADD;
|
||||
else if( sBit == "subtractscore" ) m_ScoreDisplay = SCORING_SUBTRACT;
|
||||
else if( sBit == "averagescore" ) m_ScoreDisplay = SCORING_AVERAGE;
|
||||
@@ -570,6 +592,7 @@ bool PlayerOptions::operator==( const PlayerOptions &other ) const
|
||||
COMPARE(m_fScrollBPM);
|
||||
COMPARE(m_fRandomSpeed);
|
||||
COMPARE(m_ScoreDisplay);
|
||||
COMPARE(m_FailType);
|
||||
COMPARE(m_bMuteOnError);
|
||||
COMPARE(m_fDark);
|
||||
COMPARE(m_fBlind);
|
||||
|
||||
@@ -135,6 +135,13 @@ public:
|
||||
bool m_bTransforms[NUM_TRANSFORMS];
|
||||
bool m_bMuteOnError;
|
||||
ScoreDisplay m_ScoreDisplay;
|
||||
enum FailType {
|
||||
FAIL_IMMEDIATE=0, // fail immediately when life touches 0
|
||||
FAIL_IMMEDIATE_CONTINUE, // fail immediately when life touches 0, but allow playing the rest of the song
|
||||
FAIL_AT_END, // fail if life is at 0 when the song ends
|
||||
FAIL_OFF // never fail
|
||||
};
|
||||
FailType m_FailType;
|
||||
|
||||
RString m_sNoteSkin; // "" means "no change"
|
||||
|
||||
|
||||
@@ -996,7 +996,10 @@ 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 )
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Song, m_FailType, SongOptions::FAIL_IMMEDIATE );
|
||||
{
|
||||
FOREACH_EnabledPlayerInfo( m_vPlayerInfo, pi )
|
||||
PO_GROUP_ASSIGN( pi->GetPlayerState()->m_PlayerOptions, ModsLevel_Song, m_FailType, PlayerOptions::FAIL_IMMEDIATE );
|
||||
}
|
||||
|
||||
m_textSongOptions.SetText( GAMESTATE->m_SongOptions.GetCurrent().GetString() );
|
||||
|
||||
@@ -1490,7 +1493,7 @@ void ScreenGameplay::Update( float fDeltaTime )
|
||||
{
|
||||
HealthState &hs = pi->GetPlayerState()->m_HealthState;
|
||||
HealthState OldHealthState = hs;
|
||||
if( GAMESTATE->GetPlayerFailType(pi->GetPlayerState()) != SongOptions::FAIL_OFF &&
|
||||
if( GAMESTATE->GetPlayerFailType(pi->GetPlayerState()) != PlayerOptions::FAIL_OFF &&
|
||||
pi->m_pLifeMeter && pi->m_pLifeMeter->IsFailing() )
|
||||
{
|
||||
hs = HealthState_Dead;
|
||||
@@ -1499,7 +1502,7 @@ void ScreenGameplay::Update( float fDeltaTime )
|
||||
{
|
||||
hs = HealthState_Hot;
|
||||
}
|
||||
else if( GAMESTATE->GetPlayerFailType(pi->GetPlayerState()) != SongOptions::FAIL_OFF &&
|
||||
else if( GAMESTATE->GetPlayerFailType(pi->GetPlayerState()) != PlayerOptions::FAIL_OFF &&
|
||||
pi->m_pLifeMeter && pi->m_pLifeMeter->IsInDanger() )
|
||||
{
|
||||
hs = HealthState_Danger;
|
||||
@@ -1539,10 +1542,10 @@ void ScreenGameplay::Update( float fDeltaTime )
|
||||
{
|
||||
PlayerNumber pn = pi->GetStepsAndTrailIndex();
|
||||
|
||||
SongOptions::FailType ft = GAMESTATE->GetPlayerFailType( pi->GetPlayerState() );
|
||||
PlayerOptions::FailType ft = GAMESTATE->GetPlayerFailType( pi->GetPlayerState() );
|
||||
SongOptions::LifeType lt = GAMESTATE->m_SongOptions.GetCurrent().m_LifeType;
|
||||
|
||||
if( ft == SongOptions::FAIL_OFF || ft == SongOptions::FAIL_AT_END )
|
||||
if( ft == PlayerOptions::FAIL_OFF || ft == PlayerOptions::FAIL_AT_END )
|
||||
continue;
|
||||
|
||||
// check for individual fail
|
||||
@@ -1570,7 +1573,7 @@ void ScreenGameplay::Update( float fDeltaTime )
|
||||
bAllowOniDie = true;
|
||||
break;
|
||||
}
|
||||
if( bAllowOniDie && ft == SongOptions::FAIL_IMMEDIATE )
|
||||
if( bAllowOniDie && ft == PlayerOptions::FAIL_IMMEDIATE )
|
||||
{
|
||||
if( !STATSMAN->m_CurStageStats.AllFailed() ) // if not the last one to fail
|
||||
{
|
||||
@@ -1586,18 +1589,18 @@ void ScreenGameplay::Update( float fDeltaTime )
|
||||
bool bAllFailed = true;
|
||||
FOREACH_EnabledPlayerInfo( m_vPlayerInfo, pi )
|
||||
{
|
||||
SongOptions::FailType ft = GAMESTATE->GetPlayerFailType( pi->GetPlayerState() );
|
||||
PlayerOptions::FailType ft = GAMESTATE->GetPlayerFailType( pi->GetPlayerState() );
|
||||
switch( ft )
|
||||
{
|
||||
case SongOptions::FAIL_IMMEDIATE:
|
||||
case PlayerOptions::FAIL_IMMEDIATE:
|
||||
if( pi->m_pLifeMeter && !pi->m_pLifeMeter->IsFailing() )
|
||||
bAllFailed = false;
|
||||
break;
|
||||
case SongOptions::FAIL_IMMEDIATE_CONTINUE:
|
||||
case SongOptions::FAIL_AT_END:
|
||||
case PlayerOptions::FAIL_IMMEDIATE_CONTINUE:
|
||||
case PlayerOptions::FAIL_AT_END:
|
||||
bAllFailed = false; // wait until the end of the song to fail.
|
||||
break;
|
||||
case SongOptions::FAIL_OFF:
|
||||
case PlayerOptions::FAIL_OFF:
|
||||
bAllFailed = false; // never fail.
|
||||
break;
|
||||
default:
|
||||
@@ -2328,7 +2331,7 @@ void ScreenGameplay::HandleScreenMessage( const ScreenMessage SM )
|
||||
FOREACH_EnabledPlayerInfo( m_vPlayerInfo, pi )
|
||||
{
|
||||
/* Mark failure. */
|
||||
if( GAMESTATE->GetPlayerFailType(pi->GetPlayerState()) != SongOptions::FAIL_OFF &&
|
||||
if( GAMESTATE->GetPlayerFailType(pi->GetPlayerState()) != PlayerOptions::FAIL_OFF &&
|
||||
(pi->m_pLifeMeter && pi->m_pLifeMeter->IsFailing()) )
|
||||
pi->GetPlayerStageStats()->m_bFailed = true;
|
||||
|
||||
|
||||
@@ -207,7 +207,6 @@ void ScreenJukebox::Init()
|
||||
PO_GROUP_ASSIGN_N( GAMESTATE->m_pPlayerState[p]->m_PlayerOptions, ModsLevel_Stage, m_fEffects, PlayerOptions::EFFECT_MINI, 1.0f );
|
||||
}
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_LifeType, SongOptions::LIFE_BATTERY );
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_FailType, SongOptions::FAIL_OFF );
|
||||
}
|
||||
|
||||
FOREACH_EnabledPlayer( p )
|
||||
@@ -228,7 +227,8 @@ void ScreenJukebox::Init()
|
||||
GAMESTATE->GetDefaultSongOptions( so );
|
||||
GAMESTATE->m_SongOptions.Assign( ModsLevel_Stage, so );
|
||||
|
||||
SO_GROUP_ASSIGN( GAMESTATE->m_SongOptions, ModsLevel_Stage, m_FailType, SongOptions::FAIL_OFF );
|
||||
FOREACH_EnabledPlayer( p )
|
||||
PO_GROUP_ASSIGN( GAMESTATE->m_pPlayerState[p]->m_PlayerOptions, ModsLevel_Stage, m_FailType, PlayerOptions::FAIL_OFF );
|
||||
|
||||
GAMESTATE->m_bDemonstrationOrJukebox = true;
|
||||
|
||||
|
||||
@@ -441,9 +441,9 @@ static void DefaultFailType( int &sel, bool ToSel, const ConfOption *pConfOption
|
||||
{
|
||||
if( ToSel )
|
||||
{
|
||||
SongOptions so;
|
||||
so.FromString( PREFSMAN->m_sDefaultModifiers );
|
||||
sel = so.m_FailType;
|
||||
PlayerOptions po;
|
||||
po.FromString( PREFSMAN->m_sDefaultModifiers );
|
||||
sel = po.m_FailType;
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -453,10 +453,10 @@ static void DefaultFailType( int &sel, bool ToSel, const ConfOption *pConfOption
|
||||
|
||||
switch( sel )
|
||||
{
|
||||
case 0: so.m_FailType = SongOptions::FAIL_IMMEDIATE; break;
|
||||
case 1: so.m_FailType = SongOptions::FAIL_IMMEDIATE_CONTINUE; break;
|
||||
case 2: so.m_FailType = SongOptions::FAIL_AT_END; break;
|
||||
case 3: so.m_FailType = SongOptions::FAIL_OFF; break;
|
||||
case 0: po.m_FailType = PlayerOptions::FAIL_IMMEDIATE; break;
|
||||
case 1: po.m_FailType = PlayerOptions::FAIL_IMMEDIATE_CONTINUE; break;
|
||||
case 2: po.m_FailType = PlayerOptions::FAIL_AT_END; break;
|
||||
case 3: po.m_FailType = PlayerOptions::FAIL_OFF; break;
|
||||
default:
|
||||
ASSERT(0);
|
||||
}
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
#include "GameState.h"
|
||||
#include "ThemeManager.h"
|
||||
#include "PrefsManager.h"
|
||||
#include "PlayerState.h"
|
||||
|
||||
REGISTER_SCREEN_CLASS( ScreenSongOptions );
|
||||
|
||||
@@ -22,11 +23,13 @@ void ScreenSongOptions::Init()
|
||||
|
||||
void ScreenSongOptions::ExportOptions( int iRow, const vector<PlayerNumber> &vpns )
|
||||
{
|
||||
const SongOptions::FailType ft = GAMESTATE->m_SongOptions.GetPreferred().m_FailType;
|
||||
PlayerNumber pn = GAMESTATE->m_MasterPlayerNumber;
|
||||
PlayerState *pPS = GAMESTATE->m_pPlayerState[pn];
|
||||
const PlayerOptions::FailType ft = pPS->m_PlayerOptions.GetPreferred().m_FailType;
|
||||
|
||||
ScreenOptionsMaster::ExportOptions( iRow, vpns );
|
||||
|
||||
if( ft != GAMESTATE->m_SongOptions.GetPreferred().m_FailType )
|
||||
if( ft != pPS->m_PlayerOptions.GetPreferred().m_FailType )
|
||||
GAMESTATE->m_bChangedFailTypeOnScreenSongOptions = true;
|
||||
}
|
||||
|
||||
|
||||
@@ -9,7 +9,6 @@ void SongOptions::Init()
|
||||
m_LifeType = LIFE_BAR;
|
||||
m_DrainType = DRAIN_NORMAL;
|
||||
m_iBatteryLives = 4;
|
||||
m_FailType = FAIL_IMMEDIATE;
|
||||
m_bAssistClap = false;
|
||||
m_bAssistMetronome = false;
|
||||
m_fMusicRate = 1.0f;
|
||||
@@ -74,15 +73,6 @@ void SongOptions::GetMods( vector<RString> &AddTo ) const
|
||||
}
|
||||
|
||||
|
||||
switch( m_FailType )
|
||||
{
|
||||
case FAIL_IMMEDIATE: break;
|
||||
case FAIL_IMMEDIATE_CONTINUE: AddTo.push_back("FailImmediateContinue"); break;
|
||||
case FAIL_AT_END: AddTo.push_back("FailAtEnd"); break;
|
||||
case FAIL_OFF: AddTo.push_back("FailOff"); break;
|
||||
default: ASSERT(0);
|
||||
}
|
||||
|
||||
if( m_fMusicRate != 1 )
|
||||
{
|
||||
RString s = ssprintf( "%2.2f", m_fMusicRate );
|
||||
@@ -182,19 +172,6 @@ void SongOptions::FromString( const RString &sOptions )
|
||||
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;
|
||||
else if( sBit == "failarcade" ||
|
||||
sBit == "failimmediate" ) m_FailType = FAIL_IMMEDIATE;
|
||||
else if( sBit == "failendofsong" ||
|
||||
sBit == "failimmediatecontinue" ) m_FailType = FAIL_IMMEDIATE_CONTINUE;
|
||||
else if( sBit == "failatend" ) m_FailType = FAIL_AT_END;
|
||||
else if( sBit == "failoff" ) m_FailType = FAIL_OFF;
|
||||
|
||||
else if( sBit == "faildefault" )
|
||||
{
|
||||
SongOptions so;
|
||||
GAMESTATE->GetDefaultSongOptions( so );
|
||||
m_FailType = so.m_FailType;
|
||||
}
|
||||
|
||||
else if( sBit == "clap" ) m_bAssistClap = on;
|
||||
else if( sBit == "metronome" ) m_bAssistMetronome = on;
|
||||
@@ -224,7 +201,6 @@ bool SongOptions::operator==( const SongOptions &other ) const
|
||||
COMPARE( m_LifeType );
|
||||
COMPARE( m_DrainType );
|
||||
COMPARE( m_iBatteryLives );
|
||||
COMPARE( m_FailType );
|
||||
COMPARE( m_fMusicRate );
|
||||
COMPARE( m_fHaste );
|
||||
COMPARE( m_bAssistClap );
|
||||
|
||||
@@ -22,12 +22,6 @@ public:
|
||||
};
|
||||
DrainType m_DrainType; // only used with LifeBar
|
||||
int m_iBatteryLives;
|
||||
enum FailType {
|
||||
FAIL_IMMEDIATE=0, // fail immediately when life touches 0
|
||||
FAIL_IMMEDIATE_CONTINUE, // fail immediately when life touches 0, but allow playing the rest of the song
|
||||
FAIL_AT_END, // fail if life is at 0 when the song ends
|
||||
FAIL_OFF }; // never fail
|
||||
FailType m_FailType;
|
||||
float m_fMusicRate, m_SpeedfMusicRate;
|
||||
float m_fHaste, m_SpeedfHaste;
|
||||
bool m_bAssistClap;
|
||||
|
||||
Reference in New Issue
Block a user