Skip to content

Commit

Permalink
Prefer old explicit leader as soft leader after disabling it.
Browse files Browse the repository at this point in the history
  • Loading branch information
daschuer committed Sep 29, 2023
1 parent 8da9185 commit a3a3e02
Show file tree
Hide file tree
Showing 3 changed files with 38 additions and 21 deletions.
53 changes: 32 additions & 21 deletions src/engine/sync/enginesync.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,7 @@ void EngineSync::requestSyncMode(Syncable* pSyncable, SyncMode mode) {
// decks that need to change as a result.
Syncable* oldLeader = m_pLeaderSyncable;
switch (mode) {
case SyncMode::LeaderExplicit:
case SyncMode::LeaderSoft: {
case SyncMode::LeaderExplicit: {
if (pSyncable->getBaseBpm().isValid()) {
activateLeader(pSyncable, mode);
} else {
Expand All @@ -58,21 +57,27 @@ void EngineSync::requestSyncMode(Syncable* pSyncable, SyncMode mode) {
}
break;
}
case SyncMode::Follower: {
// A request for follower mode may be converted into an enabling of soft
// leader mode if this still be best choice
if (m_pLeaderSyncable == pSyncable) {
// Avoid that pickLeader() returns pSyncable with SyncMode::LeaderExplicit
m_pLeaderSyncable = nullptr;
}
Syncable* newLeader = pickLeader(pSyncable);
if (newLeader != pSyncable) {
activateFollower(pSyncable);
case SyncMode::LeaderSoft: {
if (pSyncable->getBaseBpm().isValid() &&
pSyncable->isPlaying() &&
pSyncable->isAudible()) {
activateLeader(pSyncable, mode);
break;
}
if (newLeader && newLeader != m_pLeaderSyncable) {
[[fallthrough]];
}
case SyncMode::Follower: {
Syncable* pNewLeader = pickNewLeader(pSyncable);
if (pNewLeader == pSyncable) {
// A request for follower mode may be converted into an enabling of soft
// leader mode if this still be best choice
activateLeader(pNewLeader, SyncMode::LeaderSoft);
} else if (pNewLeader != m_pLeaderSyncable) {
// if the leader has changed, activate it (this updates m_pLeaderSyncable)
// But don't make an an explicit leader soft.
activateLeader(newLeader, SyncMode::LeaderSoft);
activateLeader(pNewLeader, SyncMode::LeaderSoft);
} else {
activateFollower(pSyncable);
}
break;
}
Expand Down Expand Up @@ -201,23 +206,29 @@ void EngineSync::deactivateSync(Syncable* pSyncable) {
}

if (wasLeader) {
Syncable* newLeader = pickLeader(nullptr);
Syncable* newLeader = pickNewLeader(nullptr);
if (newLeader != nullptr) {
activateLeader(newLeader, SyncMode::LeaderSoft);
}
}
}

Syncable* EngineSync::pickLeader(Syncable* enabling_syncable) {
if (kLogger.traceEnabled()) {
kLogger.trace() << "EngineSync::pickLeader";
}
Syncable* EngineSync::pickLeader(Syncable* pEnablingSyncable) {
if (m_pLeaderSyncable &&
m_pLeaderSyncable->getSyncMode() == SyncMode::LeaderExplicit &&
m_pLeaderSyncable->getBaseBpm().isValid()) {
if (kLogger.traceEnabled()) {
kLogger.trace() << "EngineSync::pickLeader(): explicit leader found ";
}
return m_pLeaderSyncable;
}
return pickNewLeader(pEnablingSyncable);
}

Syncable* EngineSync::pickNewLeader(Syncable* pEnablingSyncable) {
if (kLogger.traceEnabled()) {
kLogger.trace() << "EngineSync::pickNewLeader";
}
// First preference: some other sync deck that is playing.
// Note, if we are using PREFER_LOCK_BPM we don't use this option.
Syncable* first_other_playing_deck = nullptr;
Expand All @@ -235,7 +246,7 @@ Syncable* EngineSync::pickLeader(Syncable* enabling_syncable) {
continue;
}

if (pSyncable != enabling_syncable) {
if (pSyncable != pEnablingSyncable) {
if (!pSyncable->getChannel()->isPrimaryDeck()) {
continue;
}
Expand All @@ -248,7 +259,7 @@ Syncable* EngineSync::pickLeader(Syncable* enabling_syncable) {
if (playing_deck_count == 0) {
first_playing_deck = pSyncable;
}
if (!first_other_playing_deck && pSyncable != enabling_syncable) {
if (!first_other_playing_deck && pSyncable != pEnablingSyncable) {
first_other_playing_deck = pSyncable;
}
playing_deck_count++;
Expand Down
4 changes: 4 additions & 0 deletions src/engine/sync/enginesync.h
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,10 @@ class EngineSync : public SyncableListener {
/// Iterate over decks, and based on sync and play status, pick a new Leader.
/// if enabling_syncable is not null, we treat it as if it were enabled because we may
/// be in the process of enabling it.
Syncable* pickNewLeader(Syncable* enabling_syncable);

/// Return the explicit leader if the one has been selected or picks a new leader using
/// pickNewLeader();
Syncable* pickLeader(Syncable* enabling_syncable);

/// Find a deck to match against, used in the case where there is no sync Leader.
Expand Down
2 changes: 2 additions & 0 deletions src/engine/sync/synccontrol.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -519,6 +519,8 @@ void SyncControl::slotSyncLeaderEnabledChangeRequest(double state) {
// Turning off leader goes back to follower mode.
switch (mode) {
case SyncMode::LeaderExplicit:
m_pChannel->getEngineBuffer()->requestSyncMode(SyncMode::LeaderSoft);
break;
case SyncMode::LeaderSoft:
m_pChannel->getEngineBuffer()->requestSyncMode(SyncMode::Follower);
break;
Expand Down

0 comments on commit a3a3e02

Please sign in to comment.