Maelstrom: Minor improvements to the ping handling

https://github.com/libsdl-org/Maelstrom/commit/b078e452e482158fa9f2cfc8cbf860d360752c58

From b078e452e482158fa9f2cfc8cbf860d360752c58 Mon Sep 17 00:00:00 2001
From: Sam Lantinga <[EMAIL REDACTED]>
Date: Tue, 8 Nov 2011 02:33:27 -0500
Subject: [PATCH] Minor improvements to the ping handling

---
 netlogic/gameinfo.cpp | 61 ++++++++++++++++++++++++++-----------------
 netlogic/gameinfo.h   |  7 ++---
 netlogic/lobby.cpp    |  4 +--
 3 files changed, 41 insertions(+), 31 deletions(-)

diff --git a/netlogic/gameinfo.cpp b/netlogic/gameinfo.cpp
index 3fadff76..d718a863 100644
--- a/netlogic/gameinfo.cpp
+++ b/netlogic/gameinfo.cpp
@@ -208,6 +208,25 @@ GameInfo::UpdateUI(GameInfoPlayer *player)
 	}
 }
 
+void
+GameInfo::InitializePing()
+{
+	for (int i = 0; i < MAX_PLAYERS; ++i) {
+		InitializePing(i);
+	}
+}
+
+void
+GameInfo::InitializePing(int index)
+{
+	if (IsNetworkPlayer(index)) {
+		GameInfoPlayer *player = GetPlayer(index);
+		player->ping.lastPing = SDL_GetTicks();
+		player->ping.roundTripTime = 0;
+		player->ping.status = PING_GOOD;
+	}
+}
+
 void
 GameInfo::UpdatePingTime(int index, Uint32 timestamp)
 {
@@ -220,36 +239,34 @@ GameInfo::UpdatePingTime(int index, Uint32 timestamp)
 
 	player = GetPlayer(index);
 	player->ping.lastPing = now;
-	player->ping.roundTripTime = elapsed;
+	if (player->ping.roundTripTime) {
+		// Use a weighted average 1/4 previous value, 3/4 new value
+		player->ping.roundTripTime = (player->ping.roundTripTime + 3*elapsed) / 4;
+	} else {
+		player->ping.roundTripTime = elapsed;
+	}
 }
 
 void
-GameInfo::InitializePing(int index)
+GameInfo::UpdatePingStatus()
 {
-	if (IsNetworkPlayer(index)) {
-		GameInfoPlayer *player = GetPlayer(index);
-		player->ping.lastPing = SDL_GetTicks();
-		player->ping.roundTripTime = 0;
-		player->ping.status = PING_GOOD;
+	for (int i = 0; i < MAX_PLAYERS; ++i) {
+		UpdatePingStatus(i);
 	}
 }
 
 void
-GameInfo::UpdatePingStatus()
+GameInfo::UpdatePingStatus(int index)
 {
-	Uint32 now;
-	Uint32 sinceLastPing;
+	GameInfoPlayer *player = GetPlayer(index);
 
-	now = SDL_GetTicks();
-	for (int i = 0; i < MAX_PLAYERS; ++i) {
-		GameInfoPlayer *player = GetPlayer(i);
-		if (!IsNetworkPlayer(i)) {
-			player->ping.status = PING_LOCAL;
-			continue;
-		}
+	if (!IsNetworkPlayer(index)) {
+		player->ping.status = PING_LOCAL;
+	} else {
+		Uint32 sinceLastPing;
 
-		sinceLastPing = int(now - player->ping.lastPing);
-		if (sinceLastPing < PING_INTERVAL) {
+		sinceLastPing = int(SDL_GetTicks() - player->ping.lastPing);
+		if (sinceLastPing < 2*PING_INTERVAL) {
 			if (player->ping.roundTripTime <= 48) {
 printf("Game 0x%8.8x: player 0x%8.8x round trip time %d (GOOD)\n", gameID, player->playerID, player->ping.roundTripTime);
 				player->ping.status = PING_GOOD;
@@ -260,9 +277,6 @@ printf("Game 0x%8.8x: player 0x%8.8x round trip time %d (OKAY)\n", gameID, playe
 printf("Game 0x%8.8x: player 0x%8.8x round trip time %d (BAD)\n", gameID, player->playerID, player->ping.roundTripTime);
 				player->ping.status = PING_BAD;
 			}
-		} else if (sinceLastPing < 2*PING_INTERVAL) {
-printf("Game 0x%8.8x: player 0x%8.8x since last ping %d (OKAY)\n", gameID, player->playerID, sinceLastPing);
-			player->ping.status = PING_OKAY;
 		} else if (sinceLastPing < PING_TIMEOUT) {
 printf("Game 0x%8.8x: player 0x%8.8x since last ping %d (BAD)\n", gameID, player->playerID, sinceLastPing);
 			player->ping.status = PING_BAD;
@@ -270,7 +284,6 @@ printf("Game 0x%8.8x: player 0x%8.8x since last ping %d (BAD)\n", gameID, player
 printf("Game 0x%8.8x: player 0x%8.8x since last ping %d (TIMEDOUT)\n", gameID, player->playerID, sinceLastPing);
 			player->ping.status = PING_TIMEDOUT;
 		}
-
-		UpdateUI(player);
 	}
+	UpdateUI(player);
 }
diff --git a/netlogic/gameinfo.h b/netlogic/gameinfo.h
index ec00323e..639a4422 100644
--- a/netlogic/gameinfo.h
+++ b/netlogic/gameinfo.h
@@ -148,14 +148,11 @@ class GameInfo
 	void UpdateUI();
 	void UpdateUI(GameInfoPlayer *player);
 
-	void InitializePing() {
-		for (int i = 0; i < MAX_PLAYERS; ++i) {
-			InitializePing(i);
-		}
-	}
+	void InitializePing();
 	void InitializePing(int index);
 	void UpdatePingTime(int index, Uint32 timestamp);
 	void UpdatePingStatus();
+	void UpdatePingStatus(int index);
 
 	PING_STATUS GetPingStatus(int index) {
 		if (IsNetworkPlayer(index)) {
diff --git a/netlogic/lobby.cpp b/netlogic/lobby.cpp
index 677271aa..c39fc038 100644
--- a/netlogic/lobby.cpp
+++ b/netlogic/lobby.cpp
@@ -350,7 +350,7 @@ LobbyDialogDelegate::CheckPings()
 		int i = 0;
 		while (i < m_gameList.length()) {
 			GameInfo &game = m_gameList[i];
-			game.UpdatePingStatus();
+			game.UpdatePingStatus(HOST_PLAYER);
 			if (game.GetPingStatus(HOST_PLAYER) == PING_TIMEDOUT) {
 //printf("Game timed out, removing from list\n");
 				m_gameList.remove(game);
@@ -805,7 +805,7 @@ LobbyDialogDelegate::ProcessGameInfo(DynamicPacket &packet)
 		}
 		if (timestamp) {
 			m_gameList[i].UpdatePingTime(HOST_PLAYER, timestamp);
-			m_gameList[i].UpdatePingStatus();
+			m_gameList[i].UpdatePingStatus(HOST_PLAYER);
 		}
 	} else {
 		if (game.gameID != m_game.gameID) {