-
Notifications
You must be signed in to change notification settings - Fork 6
How to save and read data to from files
In computer science, in the context of data storage, serialization (or serialisation) is the process of translating data structures or object state into a [...] file [...]
The opposite operation, extracting a data structure from a series of bytes, is deserialization
~ From Wikipedia, the free encyclopedia
To save data into a file and read it again with Salty Engine, we use stdf, which is already included.
How to read/save data from/to a file:
- You make the class(es) (e.g. a
GameObject
) that need to save data implementde.edgelord.saltyengine.io.serialization.Serializable
- You override the methods
void serialize(Species)
andvoid deserialize(Species)
, as well asString getDataSetName()
- You add the class to the
de.edgelord.saltyengine.io.serialization.Serializer
- Use
void doSerialization(String)
orvoid doSerialization()
to save the data andvoid doDeserialization(String)
orvoid doDeserialization()
to read it again.
Now, in details:
- and 2. Code example (from de.edgelord.saltyengine.example.serialization):
import de.edgelord.saltyengine.io.serialization.Serializable;
import de.edgelord.stdf.Species;
import de.edgelord.stdf.reading.ValueToDataConverter;
public class Saver implements Serializable {
private int highScore = 99;
@Override
public void serialize(Species species) {
// This method saves the data. With the given Species, you can add tags and values to the file
// for example the Integer highScore, saved with the tag-name "highScore". You could use any other name there
species.addTag("highScore", highScore);
// And that's it. The data is being saved into a file!
}
@Override
public void deserialize(Species species) {
// This method reads the data. With the given Species, you can read tag values. All tags you add to the species won't be
// saved. You could say that the given Species is read-only.
// ValueToDataConverter.convertToInteger converts the given value from the given species to an integer. There are more
// types available.
// ValueToListConverter converts a value to a list, see more in the class "AdvancedSaver"
//
// You can also read a String by simply calling species.getTagValue("highScore");
highScore = ValueToDataConverter.convertToInteger(species, "highScore");
}
@Override
public String getDataSetName() {
return "saver";
}
}
- and 4. Code example (from de.edgelord.saltyengine.example.serialization):
import de.edgelord.saltyengine.io.serialization.Serializer;
import java.io.IOException;
public class SerializationMain {
public static void main(String[] args) {
Game.init(GameConfig.config(0, 0, "Serialization Example", 5));
// Add a new Saver to the list
Serializer.add(new Saver());
// read the data from the default save-file, called "save0.sdb".
// you could also call e.g. Serializer.doDeserialization("save1") or Serializer.doDeserialization("unicorn")
// When the file does not exist, it's being created and nothing is being read.
//
// It should be
// in [Your homefolder]/.[game name]
// In this example, we set the game name to be "Serialization Example" in the Game#init call.
// The method could throw an IOException, so we have to put it into a try/catch structure.
try {
Serializer.doDeserialization();
} catch (IOException e) {
e.printStackTrace();
}
// save the data to the file. That also happens automatically when you close the game-window.
// You could also save to a custom file by using
// Serializer.doSerialization("save1"); or
// Serializer.doSerialization("unicorn");
try {
Serializer.doSerialization();
} catch (IOException e) {
e.printStackTrace();
}
}
}
When you run that for the first time, You will se this message:
Never serialized something for saver so cannot deserialize for it!
That is because you never saved something to this file before. On the second and every further run, this message should not appear. You can save and read as many tags as you want, there are no limits (except for the files-size eventually).
And lastly, here is a little more extended example (from AdvancedSaver
):
import de.edgelord.saltyengine.core.Game;
import de.edgelord.saltyengine.io.serialization.Serializable;
import de.edgelord.saltyengine.transform.Vector2f;
import de.edgelord.stdf.Species;
import de.edgelord.stdf.reading.ValueToDataConverter;
import de.edgelord.stdf.reading.ValueToListConverter;
import java.util.List;
public class AdvancedSaver implements Serializable {
private int counter = 0;
private final String CAMERA_POSITION_TAG = "camPos";
private final String COUNTER_TAG = "counter";
private final String REDUNDANT_MESSAGE_TAG = "message";
@Override
public void serialize(Species species) {
species.addTag(COUNTER_TAG, ++counter);
species.addTag(REDUNDANT_MESSAGE_TAG, "This is a redundant message to show that you don't have to encode spaces with these weird combinations of stars and underscores any more!");
species.addTag(CAMERA_POSITION_TAG, Game.getCamera().getX() + "," + Game.getCamera().getY());
}
@Override
public void deserialize(Species species) {
counter = ValueToDataConverter.convertToInteger(species, COUNTER_TAG);
List<String> cameraPosition = ValueToListConverter.convertToList(species, CAMERA_POSITION_TAG, ",");
Game.getCamera().setPosition(new Coordinates2f(Float.valueOf(cameraPosition.get(0)), Float.valueOf(cameraPosition.get(1))));
System.out.println("This example started " + counter + " times before on this computer!");
System.out.println(species.getTagValue(REDUNDANT_MESSAGE_TAG));
}
@Override
public String getDataSetName() {
return "advancedSaver";
}
}
This example also shows how you can store and read the position of the camera, with the following structure:
-
species.addTag(CAMERA_POSITION_TAG, Game.getCamera().getX() + "," + Game.getCamera().getY());
adds a tag with the name "camPos" and the value x,y to the file. x and y being the coordinates of the camera. It looks e.g. like this:(camPos)3.14,314(*camPos)
-
List<String> cameraPosition = ValueToListConverter.convertToList(species, CAMERA_POSITION_TAG, ",");
creates a new list with the content of the tag "camPos", separated by "," -
Game.getCamera().setPosition(new Vector2f(Float.valueOf(cameraPosition.get(0)), Float.valueOf(cameraPosition.get(1))));
sets the first item in the list as the x and the second element as the y coordinate of the camera
After you ran this the first time, there should be a file in [your-homefolder]/.[game-name] called save0.sdb with the following content:
{saver}(highScore)99(*highScore){*saver}{advancedSaver}(camPos)0.0,0.0(*camPos)(message)This is a redundant message to show that you don't have to encode spaces with these weird combinations of stars and underscores any more!(*message)(counter)1(*counter){*advancedSaver}
Yes, everything in one line. But that is okay, because you don't want the user to edit this content by himself and may confuse or scare him off. But after a little work, you can clearly see how the data is being stored:
{saver}
(highScore)99(*highScore)
{*saver}
{advancedSaver}
(camPos)0.0,0.0(*camPos)
(message)This is a redundant message to show that you don't have to encode spaces with these weird combinations of stars and underscores any more!(*message)
(counter)1(*counter)
{*advancedSaver}
If you would save the file like that, stdf would still be able to read it.