Selaa lähdekoodia

Adopt turn timer to battle refactoring

nordsoft 2 vuotta sitten
vanhempi
sitoutus
7b4b01a280

+ 4 - 6
server/CGameHandler.cpp

@@ -1066,10 +1066,8 @@ void CGameHandler::run(bool resume)
 				{
 					turnTimerHandler.onPlayerMakingTurn(gs->players[playerColor], waitTime);
 					if(gs->curB)
-					{
-						turnTimerHandler.onBattleLoop(gs->players[gs->curB->getSidePlayer(BattleSide::ATTACKER)], waitTime);
-						turnTimerHandler.onBattleLoop(gs->players[gs->curB->getSidePlayer(BattleSide::DEFENDER)], waitTime);
-					}
+						turnTimerHandler.onBattleLoop(waitTime);
+
 					static time_duration p = milliseconds(waitTime);
 					states.cv.timed_wait(lock, p);
 				}
@@ -1272,11 +1270,11 @@ bool CGameHandler::moveHero(ObjectInstanceID hid, int3 dst, ui8 teleporting, boo
 
 		if(!transit)
 		{
-			for(auto topQuery = queries.topQuery(h->tempOwner); true; topQuery = queries.topQuery(h->tempOwner))
+			for(auto topQuery = queries->topQuery(h->tempOwner); true; topQuery = queries->topQuery(h->tempOwner))
 			{
 				moveQuery = std::dynamic_pointer_cast<CHeroMovementQuery>(topQuery);
 				if(moveQuery)
-					queries.popIfTop(moveQuery);
+					queries->popIfTop(moveQuery);
 				else
 					break;
 			}

+ 2 - 2
server/CGameHandler.h

@@ -83,8 +83,6 @@ class CGameHandler : public IGameCallback, public CBattleInfoCallback, public En
 	CVCMIServer * lobby;
 	std::shared_ptr<CApplier<CBaseForGHApply>> applier;
 
-	TurnTimerHandler turnTimerHandler;
-
 public:
 	using CCallbackBase::setBattle;
 
@@ -108,6 +106,8 @@ public:
 
 
 	SpellCastEnvironment * spellEnv;
+	
+	TurnTimerHandler turnTimerHandler;
 
 	const Services * services() const override;
 	const BattleCb * battle() const override;

+ 56 - 32
server/TurnTimerHandler.cpp

@@ -10,11 +10,14 @@
 #include "StdInc.h"
 #include "TurnTimerHandler.h"
 #include "CGameHandler.h"
+#include "battles/BattleProcessor.h"
+#include "queries/QueriesProcessor.h"
 #include "../lib/battle/BattleInfo.h"
 #include "../lib/gameState/CGameState.h"
 #include "../lib/CPlayerState.h"
 #include "../lib/CStack.h"
 #include "../lib/StartInfo.h"
+#include "../lib/NetPacks.h"
 
 TurnTimerHandler::TurnTimerHandler(CGameHandler & gh):
 	gameHandler(gh)
@@ -80,7 +83,7 @@ void TurnTimerHandler::onPlayerMakingTurn(PlayerState & state, int waitTime)
 			state.turnTimer.baseTimer = 0;
 			onPlayerMakingTurn(state, waitTime);
 		}
-		else if(!gameHandler.queries.topQuery(state.color)) //wait for replies to avoid pending queries
+		else if(!gameHandler.queries->topQuery(state.color)) //wait for replies to avoid pending queries
 			gameHandler.states.players.at(state.color).makingTurn = false; //force end turn
 	}
 }
@@ -101,59 +104,80 @@ void TurnTimerHandler::onBattleStart(PlayerState & state)
 	}
 }
 
-void TurnTimerHandler::onBattleNextStack(PlayerState & state)
+void TurnTimerHandler::onBattleNextStack(const CStack & stack)
 {
-	if(const auto * si = gameHandler.getStartInfo())
+	const auto * gs = gameHandler.gameState();
+	const auto * si = gameHandler.getStartInfo();
+	if(!si || !gs)
+		return;
+	
+	const auto & state = gs->players.at(stack.getOwner());
+	
+	if(si->turnTimerInfo.isBattleEnabled())
 	{
-		if(si->turnTimerInfo.isBattleEnabled())
-		{
-			TurnTimeUpdate ttu;
-			ttu.player = state.color;
-			ttu.turnTimer = state.turnTimer;
-			if(state.turnTimer.battleTimer < si->turnTimerInfo.battleTimer)
-				ttu.turnTimer.battleTimer = ttu.turnTimer.creatureTimer;
-			ttu.turnTimer.creatureTimer = si->turnTimerInfo.creatureTimer;
-			gameHandler.sendAndApply(&ttu);
-		}
+		TurnTimeUpdate ttu;
+		ttu.player = state.color;
+		ttu.turnTimer = state.turnTimer;
+		if(state.turnTimer.battleTimer < si->turnTimerInfo.battleTimer)
+			ttu.turnTimer.battleTimer = ttu.turnTimer.creatureTimer;
+		ttu.turnTimer.creatureTimer = si->turnTimerInfo.creatureTimer;
+		gameHandler.sendAndApply(&ttu);
 	}
 }
 
-void TurnTimerHandler::onBattleLoop(PlayerState & state, int waitTime)
+void TurnTimerHandler::onBattleLoop(int waitTime)
 {
 	const auto * gs = gameHandler.gameState();
 	const auto * si = gameHandler.getStartInfo();
 	if(!si || !gs || !gs->curB)
 		return;
 	
-	if(state.human && si->turnTimerInfo.isBattleEnabled())
+	const auto * stack = gs->curB.get()->battleGetStackByID(gs->curB->getActiveStackID());
+	if(!stack)
+		return;
+	
+	auto & state = gs->players.at(gs->curB->getSidePlayer(stack->unitSide()));
+	
+	auto turnTimerUpdateApplier = [&](const TurnTimerInfo & tTimer)
 	{
-		if(state.turnTimer.creatureTimer > 0)
+		TurnTimerInfo turnTimerUpdate = tTimer;
+		if(tTimer.creatureTimer > 0)
 		{
-			state.turnTimer.creatureTimer -= waitTime;
-			int frequency = (state.turnTimer.creatureTimer > turnTimePropagateThreshold ? turnTimePropagateFrequency : turnTimePropagateFrequencyCrit);
+			turnTimerUpdate.creatureTimer -= waitTime;
+			int frequency = (turnTimerUpdate.creatureTimer > turnTimePropagateThreshold ? turnTimePropagateFrequency : turnTimePropagateFrequencyCrit);
 			
 			if(state.status == EPlayerStatus::INGAME //do not send message if player is not active already
-			   && state.turnTimer.creatureTimer % frequency == 0)
+			   && turnTimerUpdate.creatureTimer % frequency == 0)
 			{
 				TurnTimeUpdate ttu;
 				ttu.player = state.color;
-				ttu.turnTimer = state.turnTimer;
+				ttu.turnTimer = turnTimerUpdate;
 				gameHandler.sendAndApply(&ttu);
 			}
+			return true;
 		}
-		else if(state.turnTimer.battleTimer > 0)
-		{
-			state.turnTimer.creatureTimer = state.turnTimer.battleTimer;
-			state.turnTimer.battleTimer = 0;
-			onBattleLoop(state, waitTime);
-		}
-		else if(auto * stack = const_cast<BattleInfo *>(gs->curB.get())->getStack(gs->curB->getActiveStackID()))
+		return false;
+	};
+	
+	if(state.human && si->turnTimerInfo.isBattleEnabled())
+	{
+		TurnTimerInfo turnTimer = state.turnTimer;
+		if(!turnTimerUpdateApplier(turnTimer))
 		{
-			BattleAction doNothing;
-			doNothing.actionType = EActionType::DEFEND;
-			doNothing.side = stack->unitSide();
-			doNothing.stackNumber = stack->unitId();
-			gameHandler.makeAutomaticAction(stack, doNothing);
+			if(turnTimer.battleTimer > 0)
+			{
+				turnTimer.creatureTimer = turnTimer.battleTimer;
+				turnTimer.battleTimer = 0;
+				turnTimerUpdateApplier(turnTimer);
+			}
+			else
+			{
+				BattleAction doNothing;
+				doNothing.actionType = EActionType::DEFEND;
+				doNothing.side = stack->unitSide();
+				doNothing.stackNumber = stack->unitId();
+				gameHandler.battles->makePlayerBattleAction(state.color, doNothing);
+			}
 		}
 	}
 }

+ 2 - 2
server/TurnTimerHandler.h

@@ -34,6 +34,6 @@ public:
 	void onPlayerGetTurn(PlayerState & state);
 	void onPlayerMakingTurn(PlayerState & state, int waitTime);
 	void onBattleStart(PlayerState & state);
-	void onBattleNextStack(PlayerState & state);
-	void onBattleLoop(PlayerState & state, int waitTime);
+	void onBattleNextStack(const CStack & stack);
+	void onBattleLoop(int waitTime);
 };

+ 2 - 0
server/battles/BattleFlowProcessor.cpp

@@ -315,6 +315,8 @@ void BattleFlowProcessor::activateNextStack()
 
 		if(!removeGhosts.changedStacks.empty())
 			gameHandler->sendAndApply(&removeGhosts);
+		
+		gameHandler->turnTimerHandler.onBattleNextStack(*next);
 
 		if (!tryMakeAutomaticAction(next))
 		{