Search code examples
godot4

Config file in godot not udpating the section


I am using the ConfigFile to save all the game related data into the user system.

There are two methods, one for saving the data and other one for getting the data.

Function to save the data:

func _set_data(filename: String, section: String, field: String, value):
    var config_file = ConfigFile.new()
    
    config_file.set_value(section, field, value)
    
    config_file.save(filename)

Function to get the data:

func _get_data(filename: String, section: String, field: String, default_value):
    var config_file = ConfigFile.new()

    config_file.load(filename)
    
    var result = config_file.get_value(section, field)

    if result == null:
        config_file.set_value(section, field, default_value)
        
        result = default_value
        
        config_file.save(filename)
    
    return result

Abstract functions to use these private functions outside the file indirectly:

func set_world(value: int):
    _set_data(app_config_file, world_section, world, value)

func get_world():
    return _get_data(app_config_file, world_section, world, 1)

func set_level(value: int):
    _set_data(app_config_file, level_section, level, value)

func get_level():
    return _get_data(app_config_file, level_section, level, 1)

//config file and section are basically strings

There is no issue in using these alone(for single data), but having issue in saving multiple sections at once!

For eg:

    set_level(2)
    
    set_world(4)
    
    print(get_level())
    print(get_world())

Expected output:

2
4

Actual output:

1
4

Same if I am calling save_world before and save_level after.

Research done: Whenever I am calling another function which saved other data, then it is removing the data related to the first 'set' function called.


Solution

  • Read this code:

    func _set_data(filename: String, section: String, field: String, value):
        var config_file = ConfigFile.new()
        
        config_file.set_value(section, field, value)
        
        config_file.save(filename)
    

    It creates a new ConfigFile, sets a value (a single value), and saves it to storage, replacing whatever was there.

    The gist of it is that you need all the data in the ConfigFile before saving it (or you are going to lose data), and the best (if not only) way to get it is to load it from the file.

    You have a couple approach to choose:

    • Load the file in _set_data before modifying the data.
    • Keep the ConfigFile around instead of creating a new one every time, so you always have a copy of the contents of the file in RAM.