SM4SVN commits, all code by Chris Danford:
* 57e8159: fix handling of noteskins with an uppercase letter * 3be4d7e: track W4 full combo * f8270c6: draw glow using stroke texture
This commit is contained in:
@@ -697,7 +697,9 @@ void BitmapText::DrawPrimitives()
|
||||
for( ; i < iEnd; ++i )
|
||||
m_aVertices[i].c = attr.glow;
|
||||
}
|
||||
// draw glow using the base texture and the glow texture. Otherwise, glow looks too tame on BitmapText that has a stroke.
|
||||
DrawChars( false );
|
||||
DrawChars( true );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+43
-37
@@ -77,15 +77,15 @@ void NoteField::Unload()
|
||||
|
||||
void NoteField::CacheNoteSkin( const RString &sNoteSkin_ )
|
||||
{
|
||||
RString sNoteSkin = sNoteSkin_;
|
||||
sNoteSkin.MakeLower();
|
||||
RString sNoteSkinLower = sNoteSkin_;
|
||||
sNoteSkinLower.MakeLower();
|
||||
|
||||
if( m_NoteDisplays.find(sNoteSkin) != m_NoteDisplays.end() )
|
||||
if( m_NoteDisplays.find(sNoteSkinLower) != m_NoteDisplays.end() )
|
||||
return;
|
||||
|
||||
LockNoteSkin l( sNoteSkin );
|
||||
LockNoteSkin l( sNoteSkinLower );
|
||||
|
||||
LOG->Trace("NoteField::CacheNoteSkin: cache %s", sNoteSkin.c_str() );
|
||||
LOG->Trace("NoteField::CacheNoteSkin: cache %s", sNoteSkinLower.c_str() );
|
||||
NoteDisplayCols *nd = new NoteDisplayCols( GAMESTATE->GetCurrentStyle()->m_iColsPerPlayer );
|
||||
|
||||
for( int c=0; c<GAMESTATE->GetCurrentStyle()->m_iColsPerPlayer; c++ )
|
||||
@@ -93,26 +93,22 @@ void NoteField::CacheNoteSkin( const RString &sNoteSkin_ )
|
||||
nd->m_ReceptorArrowRow.Load( m_pPlayerState, m_fYReverseOffsetPixels );
|
||||
nd->m_GhostArrowRow.Load( m_pPlayerState, m_fYReverseOffsetPixels );
|
||||
|
||||
m_NoteDisplays[ sNoteSkin ] = nd;
|
||||
m_NoteDisplays[ sNoteSkinLower ] = nd;
|
||||
}
|
||||
|
||||
void NoteField::UncacheNoteSkin( const RString &sNoteSkin_ )
|
||||
{
|
||||
RString sNoteSkin( sNoteSkin_ );
|
||||
sNoteSkin.MakeLower();
|
||||
RString sNoteSkinLower = sNoteSkin_;
|
||||
sNoteSkinLower.MakeLower();
|
||||
|
||||
LOG->Trace("NoteField::CacheNoteSkin: release %s", sNoteSkin.c_str() );
|
||||
ASSERT_M( m_NoteDisplays.find(sNoteSkin) != m_NoteDisplays.end(), sNoteSkin );
|
||||
delete m_NoteDisplays[sNoteSkin];
|
||||
m_NoteDisplays.erase( sNoteSkin );
|
||||
LOG->Trace("NoteField::CacheNoteSkin: release %s", sNoteSkinLower.c_str() );
|
||||
ASSERT_M( m_NoteDisplays.find(sNoteSkinLower) != m_NoteDisplays.end(), sNoteSkinLower );
|
||||
delete m_NoteDisplays[sNoteSkinLower];
|
||||
m_NoteDisplays.erase( sNoteSkinLower );
|
||||
}
|
||||
|
||||
void NoteField::CacheAllUsedNoteSkins()
|
||||
{
|
||||
/* Cache all note skins that we might need for the whole song, course or battle
|
||||
* play, so we don't have to load them later (such as between course songs). */
|
||||
vector<RString> asSkins;
|
||||
|
||||
// If we're in Routine mode, apply our per-player noteskins.
|
||||
if( GAMESTATE->GetCurrentStyle()->m_StyleType == StyleType_TwoPlayersSharedSides )
|
||||
{
|
||||
@@ -120,32 +116,43 @@ void NoteField::CacheAllUsedNoteSkins()
|
||||
GAMESTATE->ApplyStageModifiers( pn, ROUTINE_NOTESKIN.GetValue(pn) );
|
||||
}
|
||||
|
||||
GAMESTATE->GetAllUsedNoteSkins( asSkins );
|
||||
asSkins.push_back( m_pPlayerState->m_PlayerOptions.GetStage().m_sNoteSkin );
|
||||
/* Cache all note skins that we might need for the whole song, course or battle
|
||||
* play, so we don't have to load them later (such as between course songs). */
|
||||
vector<RString> asSkinsLower;
|
||||
GAMESTATE->GetAllUsedNoteSkins( asSkinsLower );
|
||||
asSkinsLower.push_back( m_pPlayerState->m_PlayerOptions.GetStage().m_sNoteSkin );
|
||||
FOREACH( RString, asSkinsLower, s )
|
||||
s->MakeLower();
|
||||
|
||||
for( unsigned i=0; i < asSkins.size(); ++i )
|
||||
CacheNoteSkin( asSkins[i] );
|
||||
for( unsigned i=0; i < asSkinsLower.size(); ++i )
|
||||
CacheNoteSkin( asSkinsLower[i] );
|
||||
|
||||
/* If we're changing note skins in the editor, we can have old note skins
|
||||
* lying around. Remove them so they don't accumulate. */
|
||||
/* If we're changing note skins in the editor, we can have old note skins lying
|
||||
* around. Remove them so they don't accumulate. */
|
||||
set<RString> setNoteSkinsToUnload;
|
||||
FOREACHM( RString, NoteDisplayCols *, m_NoteDisplays, d )
|
||||
{
|
||||
if( find(asSkins.begin(), asSkins.end(), d->first) == asSkins.end() )
|
||||
bool unused = find(asSkinsLower.begin(), asSkinsLower.end(), d->first) == asSkinsLower.end();
|
||||
if( unused )
|
||||
setNoteSkinsToUnload.insert( d->first );
|
||||
}
|
||||
FOREACHS( RString, setNoteSkinsToUnload, s )
|
||||
UncacheNoteSkin( *s );
|
||||
|
||||
map<RString, NoteDisplayCols *>::iterator it = m_NoteDisplays.find( m_pPlayerState->m_PlayerOptions.GetCurrent().m_sNoteSkin );
|
||||
ASSERT_M( it != m_NoteDisplays.end(), m_pPlayerState->m_PlayerOptions.GetCurrent().m_sNoteSkin );
|
||||
RString sCurrentNoteSkinLower = m_pPlayerState->m_PlayerOptions.GetCurrent().m_sNoteSkin;
|
||||
sCurrentNoteSkinLower.MakeLower();
|
||||
|
||||
map<RString, NoteDisplayCols *>::iterator it = m_NoteDisplays.find( sCurrentNoteSkinLower );
|
||||
ASSERT_M( it != m_NoteDisplays.end(), sCurrentNoteSkinLower );
|
||||
m_pCurDisplay = it->second;
|
||||
memset( m_pDisplays, 0, sizeof(m_pDisplays) );
|
||||
|
||||
FOREACH_EnabledPlayer( pn )
|
||||
{
|
||||
const RString& sNoteSkin = GAMESTATE->m_pPlayerState[pn]->m_PlayerOptions.GetCurrent().m_sNoteSkin;
|
||||
it = m_NoteDisplays.find( sNoteSkin );
|
||||
ASSERT_M( it != m_NoteDisplays.end(), sNoteSkin );
|
||||
RString sNoteSkinLower = GAMESTATE->m_pPlayerState[pn]->m_PlayerOptions.GetCurrent().m_sNoteSkin;
|
||||
sNoteSkinLower.MakeLower();
|
||||
it = m_NoteDisplays.find( sNoteSkinLower );
|
||||
ASSERT_M( it != m_NoteDisplays.end(), sNoteSkinLower );
|
||||
m_pDisplays[pn] = it->second;
|
||||
}
|
||||
}
|
||||
@@ -177,16 +184,17 @@ void NoteField::Load(
|
||||
ssprintf("%d = %d",m_pNoteData->GetNumTracks(), GAMESTATE->GetCurrentStyle()->m_iColsPerPlayer) );
|
||||
|
||||
// The note skin may have changed at the beginning of a new course song.
|
||||
map<RString, NoteDisplayCols *>::iterator it = m_NoteDisplays.find( m_pPlayerState->m_PlayerOptions.GetCurrent().m_sNoteSkin );
|
||||
ASSERT_M( it != m_NoteDisplays.end(),
|
||||
ssprintf("Player noteskin: %s", m_pPlayerState->m_PlayerOptions.GetCurrent().m_sNoteSkin.c_str()) );
|
||||
m_pCurDisplay = it->second;
|
||||
RString sNoteSkinLower = m_pPlayerState->m_PlayerOptions.GetCurrent().m_sNoteSkin;
|
||||
sNoteSkinLower.MakeLower();
|
||||
map<RString, NoteDisplayCols *>::iterator it = m_NoteDisplays.find( sNoteSkinLower );
|
||||
ASSERT_M( it != m_NoteDisplays.end(), sNoteSkinLower );
|
||||
memset( m_pDisplays, 0, sizeof(m_pDisplays) );
|
||||
FOREACH_EnabledPlayer( pn )
|
||||
{
|
||||
const RString& sNoteSkin = GAMESTATE->m_pPlayerState[pn]->m_PlayerOptions.GetCurrent().m_sNoteSkin;
|
||||
it = m_NoteDisplays.find( sNoteSkin );
|
||||
ASSERT_M( it != m_NoteDisplays.end(), sNoteSkin );
|
||||
RString sNoteSkinLower = GAMESTATE->m_pPlayerState[pn]->m_PlayerOptions.GetCurrent().m_sNoteSkin;
|
||||
sNoteSkinLower.MakeLower();
|
||||
it = m_NoteDisplays.find( sNoteSkinLower );
|
||||
ASSERT_M( it != m_NoteDisplays.end(), sNoteSkinLower );
|
||||
m_pDisplays[pn] = it->second;
|
||||
}
|
||||
}
|
||||
@@ -686,9 +694,7 @@ void NoteField::DrawPrimitives()
|
||||
|
||||
// todo: add warp text
|
||||
|
||||
//
|
||||
// Course mods text
|
||||
//
|
||||
const Course *pCourse = GAMESTATE->m_pCurCourse;
|
||||
if( pCourse )
|
||||
{
|
||||
|
||||
+55
-38
@@ -611,8 +611,7 @@ void Player::Update( float fDeltaTime )
|
||||
|
||||
if(m_pPlayerState->m_mp != MultiPlayer_Invalid)
|
||||
{
|
||||
/*
|
||||
* In multiplayer, it takes too long to run player updates for every player each frame;
|
||||
/* In multiplayer, it takes too long to run player updates for every player each frame;
|
||||
* with 32 players and three difficulties, we have 96 Players to update. Stagger these
|
||||
* updates, by only updating a few players each update; since we don't have screen elements
|
||||
* tightly tied to user actions in this mode, this doesn't degrade gameplay. Run 4 players
|
||||
@@ -901,7 +900,7 @@ void Player::Update( float fDeltaTime )
|
||||
ApplyWaitingTransforms();
|
||||
}
|
||||
|
||||
/* Update a group of holds with shared scoring/life. All of these holds will have the same start row. */
|
||||
/* Update a group of holds with shared scoring/life. All of these holds will have the same start row. */
|
||||
void Player::UpdateHoldNotes( int iSongRow, float fDeltaTime, vector<TrackRowTapNote> &vTN )
|
||||
{
|
||||
ASSERT( !vTN.empty() );
|
||||
@@ -1026,9 +1025,10 @@ void Player::UpdateHoldNotes( int iSongRow, float fDeltaTime, vector<TrackRowTap
|
||||
|
||||
if( bInitiatedNote && fLife != 0 )
|
||||
{
|
||||
/* This hold note is not judged and we stepped on its head. Update iLastHeldRow.
|
||||
* Do this even if we're a little beyond the end of the hold note, to make sure
|
||||
* iLastHeldRow is clamped to iEndRow if the hold note is held all the way. */
|
||||
/* This hold note is not judged and we stepped on its head.
|
||||
* Update iLastHeldRow. Do this even if we're a little beyond the end
|
||||
* of the hold note, to make sure iLastHeldRow is clamped to iEndRow
|
||||
* if the hold note is held all the way. */
|
||||
FOREACH( TrackRowTapNote, vTN, trtn )
|
||||
{
|
||||
TapNote &tn = *trtn->pTN;
|
||||
@@ -1098,8 +1098,9 @@ void Player::UpdateHoldNotes( int iSongRow, float fDeltaTime, vector<TrackRowTap
|
||||
m_pSecondaryScoreKeeper->HandleHoldActiveSeconds( fSecondsActiveSinceLastUpdate );
|
||||
}
|
||||
|
||||
/* check for LetGo. If the head was missed completely, don't count an LetGo. */
|
||||
/* Why? If you never step on the head, then it will be left as HNS_None, which doesn't seem correct. */
|
||||
// check for LetGo. If the head was missed completely, don't count an LetGo.
|
||||
/* Why? If you never step on the head, then it will be left as HNS_None,
|
||||
* which doesn't seem correct. */
|
||||
if( IMMEDIATE_HOLD_LET_GO )
|
||||
{
|
||||
if( bInitiatedNote && fLife == 0 ) // the player has not pressed the button for a long time!
|
||||
@@ -1111,9 +1112,9 @@ void Player::UpdateHoldNotes( int iSongRow, float fDeltaTime, vector<TrackRowTap
|
||||
{
|
||||
bool bLetGoOfHoldNote = false;
|
||||
|
||||
/* Score rolls that end with fLife == 0 as LetGo, even if HOLD_CHECKPOINTS is on.
|
||||
* Rolls don't have iCheckpointsMissed set, so, unless we check Life == 0, rolls would always be
|
||||
* scored as Held. */
|
||||
/* Score rolls that end with fLife == 0 as LetGo, even if
|
||||
* HOLD_CHECKPOINTS is on. Rolls don't have iCheckpointsMissed set, so,
|
||||
* unless we check Life == 0, rolls would always be scored as Held. */
|
||||
bool bAllowHoldCheckpoints;
|
||||
switch( subType )
|
||||
{
|
||||
@@ -1142,7 +1143,8 @@ void Player::UpdateHoldNotes( int iSongRow, float fDeltaTime, vector<TrackRowTap
|
||||
}
|
||||
bLetGoOfHoldNote = iCheckpointsMissed > 0 || iCheckpointsHit == 0;
|
||||
|
||||
// TRICKY: If the hold is so short that it has no checkpoints, then mark it as Held if the head was stepped on.
|
||||
// TRICKY: If the hold is so short that it has no checkpoints,
|
||||
// then mark it as Held if the head was stepped on.
|
||||
if( iCheckpointsHit == 0 && iCheckpointsMissed == 0 )
|
||||
bLetGoOfHoldNote = !bSteppedOnHead;
|
||||
}
|
||||
@@ -1387,7 +1389,7 @@ int Player::GetClosestNoteDirectional( int col, int iStartRow, int iEndRow, bool
|
||||
if( !bForward )
|
||||
--begin;
|
||||
|
||||
/* Is this the row we want? */
|
||||
// Is this the row we want?
|
||||
do {
|
||||
const TapNote &tn = begin->second;
|
||||
if( tn.type == TapNote::empty )
|
||||
@@ -1405,7 +1407,7 @@ int Player::GetClosestNoteDirectional( int col, int iStartRow, int iEndRow, bool
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Find the closest note to fBeat. */
|
||||
// Find the closest note to fBeat.
|
||||
int Player::GetClosestNote( int col, int iNoteRow, int iMaxRowsAhead, int iMaxRowsBehind, bool bAllowGraded ) const
|
||||
{
|
||||
// Start at iIndexStartLookingAt and search outward.
|
||||
@@ -1460,7 +1462,7 @@ int Player::GetClosestNonEmptyRowDirectional( int iStartRow, int iEndRow, bool b
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Find the closest note to fBeat. */
|
||||
// Find the closest note to fBeat.
|
||||
int Player::GetClosestNonEmptyRow( int iNoteRow, int iMaxRowsAhead, int iMaxRowsBehind, bool bAllowGraded ) const
|
||||
{
|
||||
// Start at iIndexStartLookingAt and search outward.
|
||||
@@ -1504,7 +1506,6 @@ void Player::Fret( int col, int row, const RageTimer &tm, bool bHeld, bool bRele
|
||||
StepStrumHopo( col, row, tm, bHeld, bRelease, ButtonType_StrumFretsChanged );
|
||||
}
|
||||
|
||||
|
||||
// Handle hammer-ons and pull-offs
|
||||
const float fPositionSeconds = GAMESTATE->m_fMusicSeconds - tm.Ago();
|
||||
int iHopoCol = -1;
|
||||
@@ -1556,7 +1557,6 @@ void Player::Fret( int col, int row, const RageTimer &tm, bool bHeld, bool bRele
|
||||
if( bDoHopo )
|
||||
Hopo( iHopoCol, row, tm, bHeld, bRelease );
|
||||
|
||||
|
||||
// Check if this fret breaks all active holds.
|
||||
if( !bRelease )
|
||||
{
|
||||
@@ -1683,7 +1683,8 @@ void Player::StepStrumHopo( int col, int row, const RageTimer &tm, bool bHeld, b
|
||||
if( IsOniDead() )
|
||||
return;
|
||||
|
||||
// Do everything that depends on a RageTimer here and set your breakpoints somewhere after this block
|
||||
// Do everything that depends on a RageTimer here;
|
||||
// set your breakpoints somewhere after this block.
|
||||
const float fLastBeatUpdate = GAMESTATE->m_LastBeatUpdate.Ago();
|
||||
const float fPositionSeconds = GAMESTATE->m_fMusicSeconds - tm.Ago();
|
||||
const float fTimeSinceStep = tm.Ago();
|
||||
@@ -1824,13 +1825,17 @@ void Player::StepStrumHopo( int col, int row, const RageTimer &tm, bool bHeld, b
|
||||
}
|
||||
|
||||
// Check for step on a TapNote
|
||||
/* XXX: This seems wrong. If a player steps twice quickly and two notes are close together in the same column then
|
||||
* it is possible for the two notes to be graded out of order. Two possible fixes:
|
||||
* 1. Adjust the fSongBeat (or the resulting note row) backward by iStepSearchRows and search forward two iStepSearchRows
|
||||
* lengths, disallowing graded. This doesn't seem right because if a second note has passed, an earlier one should not
|
||||
* be graded.
|
||||
/* XXX: This seems wrong. If a player steps twice quickly and two notes are
|
||||
* close together in the same column then it is possible for the two notes
|
||||
* to be graded out of order.
|
||||
* Two possible fixes:
|
||||
* 1. Adjust the fSongBeat (or the resulting note row) backward by
|
||||
* iStepSearchRows and search forward two iStepSearchRows lengths,
|
||||
* disallowing graded. This doesn't seem right because if a second note has
|
||||
* passed, an earlier one should not be graded.
|
||||
* 2. Clamp the distance searched backward to the previous row graded.
|
||||
* Either option would fundamentally change the grading of two quick notes "jack hammers." Hmm.
|
||||
* Either option would fundamentally change the grading of two quick notes
|
||||
* "jack hammers." Hmm.
|
||||
*/
|
||||
const int iStepSearchRows = BeatToNoteRow( StepSearchDistance * GAMESTATE->m_fCurBPS * GAMESTATE->m_SongOptions.GetCurrent().m_fMusicRate );
|
||||
int iRowOfOverlappingNoteOrRow = row;
|
||||
@@ -1910,7 +1915,7 @@ void Player::StepStrumHopo( int col, int row, const RageTimer &tm, bool bHeld, b
|
||||
|
||||
case TapNote::attack:
|
||||
if( !bRelease && fSecondsFromExact <= GetWindowSeconds(TW_Attack) && !pTN->result.bHidden )
|
||||
score = TNS_W2; /* sentinel */
|
||||
score = TNS_W2; // sentinel
|
||||
break;
|
||||
|
||||
case TapNote::hold_head:
|
||||
@@ -1937,7 +1942,8 @@ void Player::StepStrumHopo( int col, int row, const RageTimer &tm, bool bHeld, b
|
||||
case PC_AUTOPLAY:
|
||||
score = PlayerAI::GetTapNoteScore( m_pPlayerState );
|
||||
|
||||
/* XXX: This doesn't make sense. Step should only be called in autoplay for hit notes */
|
||||
/* XXX: This doesn't make sense.
|
||||
* Step should only be called in autoplay for hit notes. */
|
||||
#if 0
|
||||
// GetTapNoteScore always returns TNS_W1 in autoplay.
|
||||
// If the step is far away, don't judge it.
|
||||
@@ -1949,12 +1955,12 @@ void Player::StepStrumHopo( int col, int row, const RageTimer &tm, bool bHeld, b
|
||||
}
|
||||
#endif
|
||||
|
||||
// TRICKY: We're asking the AI to judge mines. consider TNS_W4 and below
|
||||
// as "mine was hit" and everything else as "mine was avoided"
|
||||
// TRICKY: We're asking the AI to judge mines. Consider TNS_W4 and
|
||||
// below as "mine was hit" and everything else as "mine was avoided"
|
||||
if( pTN->type == TapNote::mine )
|
||||
{
|
||||
// The CPU hits a lot of mines. Only consider hitting the
|
||||
// first mine for a row. We know we're the first mine if
|
||||
// The CPU hits a lot of mines. Only consider hitting the
|
||||
// first mine for a row. We know we're the first mine if
|
||||
// there are are no mines to the left of us.
|
||||
for( int t=0; t<col; t++ )
|
||||
{
|
||||
@@ -1962,7 +1968,7 @@ void Player::StepStrumHopo( int col, int row, const RageTimer &tm, bool bHeld, b
|
||||
return; // avoid
|
||||
}
|
||||
|
||||
// The CPU hits a lot of mines. Make it less likely to hit
|
||||
// The CPU hits a lot of mines. Make it less likely to hit
|
||||
// mines that don't have a tap note on the same row.
|
||||
bool bTapsOnRow = m_NoteData.IsThereATapOrHoldHeadAtRow( iRowOfOverlappingNoteOrRow );
|
||||
TapNoteScore get_to_avoid = bTapsOnRow ? TNS_W3 : TNS_W4;
|
||||
@@ -1974,7 +1980,7 @@ void Player::StepStrumHopo( int col, int row, const RageTimer &tm, bool bHeld, b
|
||||
}
|
||||
|
||||
if( pTN->type == TapNote::attack && score > TNS_W4 )
|
||||
score = TNS_W2; /* sentinel */
|
||||
score = TNS_W2; // sentinel
|
||||
|
||||
/* AI will generate misses here. Don't handle a miss like a regular note because
|
||||
* we want the judgment animation to appear delayed. Instead, return early if
|
||||
@@ -2107,7 +2113,7 @@ done_checking_hopo:
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
// handle attack notes
|
||||
if( pTN->type == TapNote::attack && score == TNS_W2 )
|
||||
{
|
||||
score = TNS_None; // don't score this as anything
|
||||
@@ -2178,7 +2184,8 @@ done_checking_hopo:
|
||||
if( pTN->type != TapNote::mine )
|
||||
{
|
||||
const bool bBlind = (m_pPlayerState->m_PlayerOptions.GetCurrent().m_fBlind != 0);
|
||||
// XXX This is the wrong combo for shared players. STATSMAN->m_CurStageStats.m_Player[pn] might work but could be wrong.
|
||||
// XXX: This is the wrong combo for shared players.
|
||||
// STATSMAN->m_CurStageStats.m_Player[pn] might work, but could be wrong.
|
||||
const bool bBright = ( m_pPlayerStageStats && m_pPlayerStageStats->m_iCurCombo > int(BRIGHT_GHOST_COMBO_THRESHOLD) ) || bBlind;
|
||||
if( m_pNoteField )
|
||||
m_pNoteField->DidTapNote( col, bBlind? TNS_W1:score, bBright );
|
||||
@@ -2359,6 +2366,7 @@ void Player::UpdateJudgedRows()
|
||||
bool bAllJudged = true;
|
||||
const bool bSeparately = GAMESTATE->GetCurrentGame()->m_bCountNotesSeparately;
|
||||
|
||||
// todo: modify function for warps? -aj
|
||||
{
|
||||
NoteData::all_tracks_iterator iter = *m_pIterUnjudgedRows;
|
||||
int iLastSeenRow = -1;
|
||||
@@ -2366,6 +2374,12 @@ void Player::UpdateJudgedRows()
|
||||
{
|
||||
int iRow = iter.Row();
|
||||
|
||||
// if row is in a skip section, ignore it? -aj
|
||||
//if(iRow)
|
||||
//{
|
||||
// // stuff!!
|
||||
//}
|
||||
|
||||
if( iLastSeenRow != iRow )
|
||||
{
|
||||
iLastSeenRow = iRow;
|
||||
@@ -2402,6 +2416,7 @@ void Player::UpdateJudgedRows()
|
||||
}
|
||||
}
|
||||
|
||||
// handle mines.
|
||||
{
|
||||
bAllJudged = true;
|
||||
set<RageSound *> setSounds;
|
||||
@@ -2995,7 +3010,7 @@ void Player::SetCombo( int iCombo, int iMisses )
|
||||
this->PlayCommand( "ThousandMilestone" );
|
||||
|
||||
// don't show a colored combo until 1/4 of the way through the song
|
||||
bool bPastMidpoint = GAMESTATE->GetCourseSongIndex()>0 ||
|
||||
bool bPastBeginning = (!GAMESTATE->IsCourseMode() || GAMESTATE->GetCourseSongIndex()>0) &&
|
||||
GAMESTATE->m_fMusicSeconds > GAMESTATE->m_pCurSong->m_fMusicLengthSeconds/4;
|
||||
|
||||
if( m_bSendJudgmentAndComboMessages )
|
||||
@@ -3005,12 +3020,14 @@ void Player::SetCombo( int iCombo, int iMisses )
|
||||
msg.SetParam( "Combo", iCombo );
|
||||
if( iMisses )
|
||||
msg.SetParam( "Misses", iMisses );
|
||||
if( bPastMidpoint && m_pPlayerStageStats->FullComboOfScore(TNS_W1) )
|
||||
if( bPastPastBeginning && m_pPlayerStageStats->FullComboOfScore(TNS_W1) )
|
||||
msg.SetParam( "FullComboW1", true );
|
||||
if( bPastMidpoint && m_pPlayerStageStats->FullComboOfScore(TNS_W2) )
|
||||
if( bPastPastBeginning && m_pPlayerStageStats->FullComboOfScore(TNS_W2) )
|
||||
msg.SetParam( "FullComboW2", true );
|
||||
if( bPastMidpoint && m_pPlayerStageStats->FullComboOfScore(TNS_W3) )
|
||||
if( bPastPastBeginning && m_pPlayerStageStats->FullComboOfScore(TNS_W3) )
|
||||
msg.SetParam( "FullComboW3", true );
|
||||
if( bPastPastBeginning && m_pPlayerStageStats->FullComboOfScore(TNS_W4) )
|
||||
msg.SetParam( "FullComboW4", true );
|
||||
this->HandleMessage( msg );
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user