Fixed user-invisible crash on multiplayer updating thread when resuming game

This commit is contained in:
Yair Morgenstern 2023-06-12 18:19:45 +03:00
parent 1bd8c4fde7
commit 61a90a4193
2 changed files with 11 additions and 3 deletions

View File

@ -446,6 +446,8 @@ open class UncivGame(val isConsoleMode: Boolean = false) : Game(), PlatformSpeci
val curGameInfo = gameInfo val curGameInfo = gameInfo
if (curGameInfo != null) files.requestAutoSave(curGameInfo) if (curGameInfo != null) files.requestAutoSave(curGameInfo)
if (::musicController.isInitialized) musicController.pause() if (::musicController.isInitialized) musicController.pause()
// We stop the *in-game* multiplayer update, so that when we resume(), it doesn't keep working and A. we'll have errors and B. we'll have multiple updaters active
if (::onlineMultiplayer.isInitialized) onlineMultiplayer.multiplayerGameUpdater.cancel()
super.pause() super.pause()
} }

View File

@ -19,6 +19,7 @@ import com.unciv.utils.debug
import com.unciv.utils.launchOnThreadPool import com.unciv.utils.launchOnThreadPool
import com.unciv.utils.withGLContext import com.unciv.utils.withGLContext
import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Job
import kotlinx.coroutines.coroutineScope import kotlinx.coroutines.coroutineScope
import kotlinx.coroutines.delay import kotlinx.coroutines.delay
import kotlinx.coroutines.flow.flow import kotlinx.coroutines.flow.flow
@ -51,9 +52,15 @@ class OnlineMultiplayer {
private val lastCurGameRefresh: AtomicReference<Instant?> = AtomicReference() private val lastCurGameRefresh: AtomicReference<Instant?> = AtomicReference()
val games: Set<OnlineMultiplayerGame> get() = savedGames.values.toSet() val games: Set<OnlineMultiplayerGame> get() = savedGames.values.toSet()
val multiplayerGameUpdater: Job
init { init {
flow<Unit> { /** We have 2 'async processes' that update the multiplayer games:
* A. This one, which as part of *this process* runs refreshes for all OS's
* B. MultiplayerTurnCheckWorker, which *as an Android worker* runs refreshes *even when the game is closed*.
* Only for Android, obviously
*/
multiplayerGameUpdater = flow<Unit> {
while (true) { while (true) {
delay(500) delay(500)
@ -134,8 +141,7 @@ class OnlineMultiplayer {
*/ */
suspend fun addGame(gameId: String, gameName: String? = null) { suspend fun addGame(gameId: String, gameName: String? = null) {
val saveFileName = if (gameName.isNullOrBlank()) gameId else gameName val saveFileName = if (gameName.isNullOrBlank()) gameId else gameName
var gamePreview: GameInfoPreview val gamePreview: GameInfoPreview = try {
gamePreview = try {
multiplayerServer.tryDownloadGamePreview(gameId) multiplayerServer.tryDownloadGamePreview(gameId)
} catch (_: MultiplayerFileNotFoundException) { } catch (_: MultiplayerFileNotFoundException) {
// Game is so old that a preview could not be found on dropbox lets try the real gameInfo instead // Game is so old that a preview could not be found on dropbox lets try the real gameInfo instead