SaveState resetting issue

Monkey Targets Forums/Android/SaveState resetting issue

Rieha(Posted March) [#1]
I've been getting some reports of missing items and resetting high scores on my games Android version. It's rare, as I've got under 10 reports of it and there's almost 100k downloads already, but it's still a serious issue.

I haven't succeeded at reproducing the bug. I made a test app which saved and loaded the game state thousands of times with no issues, so I'm starting to think it's a device specific problem or maybe just a nasty "feature" of the OS...? At least once this bug occurred while auto updating the game.

Has anyone had similar issues with SaveState on Android? Is it possible for shared preferences to get erased while updating a game or otherwise?

Here's an example of the code I use to save and load data. Could using ~n as a separator cause problems on some rare instances? p.s. I know I could use Split, changed to manual method for bug hunting reasons long time ago. Yes, it's ugly.

''// CONFIG
Field configLevel%, configMode%, configSoundOn?

''// SAVESTATE
Field saveDataMap:StringMap<Int> = New StringMap<Int>
Field saveDataStr$
	
		
Method SaveGameState:Void()
	saveDataStr = ("123ABC" + "," + "123" + "~n")	'// old bug hunting stuff
	SaveGameAdd("configLevel", configLevel)
	SaveGameAdd("configMode", configMode)
	SaveGameAdd("configSoundOn", Int(configSoundOn))
	SaveState(saveDataStr)
End
	

Method SaveGameAdd:Void(key$, value%)
	saveDataStr += (key + "," + String(value) + "~n")
End


Method LoadGameState:Void()
	Local reset?, loadDataStr$ = LoadState()

	If loadDataStr
		Local linesLength%, line$

		saveDataMap.Clear()

		'// manual split
		Local loadDataStrLength% = loadDataStr.Length()
		Local keyName$, keyValue$, endChar%, startChar%

		If loadDataStrLength > 1
			Repeat
				endChar = loadDataStr.Find(",", startChar)
				If endChar <> -1
					If linesLength = 0
						keyName = loadDataStr[startChar .. endChar]
					Else
						keyName = loadDataStr[startChar + 1 .. endChar]
					End

					startChar = loadDataStr.Find("~n", endChar)

					If startChar <> -1
						keyValue = loadDataStr[endChar + 1 .. startChar]
						saveDataMap.Add(keyName, Int(keyValue))
						linesLength += 1
					Else
						Exit
					End
				Else
					Exit
				End
			Forever
		Else
			reset = True
		End

		If linesLength > 1	
			Local dataSetCount%

			If saveDataMap.Contains("configLevel")
				configLevel = saveDataMap.Get("configLevel"); dataSetCount += 1
			End
			If saveDataMap.Contains("configMode")
				configMode = saveDataMap.Get("configMode"); dataSetCount += 1
			End
			If saveDataMap.Contains("configSoundOn")
				configSoundOn = Bool(saveDataMap.Get("configSoundOn")); dataSetCount += 1
			End

			If dataSetCount = 0 reset = True
		End
	Else
		reset = True
	End

	If reset
	 	'// No savestate found
		configLevel = LEVEL_JAPAN
		configMode = GAMEMODE_ARCADE
		configSoundOn = True
	End
End



Xaron(Posted March) [#2]
That's most probably a device related bug. You cannot imagine how many stupid people are out there doing fancy stuff with device explorers on their rooted phones and ooops after that blaming the devs because something went wrong. Plus Android itself might have issues in specific versions on specific phones... And then there is this crap of SD cards out there which sometimes fail as well.

The only thing you could do is to use Google Play Services instead and store that stuff in the cloud.


Rieha(Posted March) [#3]
Play Services cloud storage could be really nice, but would take some researching and testing as I have no idea how it works. Reliable local saving is important nonetheless, as those who aren't logged in will still get mad if data is lost.

I changed the save system a bit already. Some people have had problems with special characters with shared preferences so I changed the ~n separator, just in case. There's also now a back up file saved in the internal storage.


Rieha(Posted March) [#4]
double post