'How to conform a custom object to Codable

I've been trying to save a UserData object so that content is "permanent". All of the methods online show classes with primitive types like String, Int, Double, etc. I am aware that you can store Data types but I couldn't find much

This is the class I want to save to disk. It errors out with : "Type 'UserData' does not conform to protocol 'Decodable'" and "Type 'UserData' does not conform to protocol 'Encodable'"

Obviously, skillBag is causing the issue; but I can't find any resources on how to conform Skill to Codable.

class UserData : ObservableObject, Codable{
    private var userName:String;
    @Published private var skillBag:[Skill] = [];
    
    init(Username user:String, skillBag skills:[Skill]) {
        userName = user;
        skillBag = skills;
    }
 }

Skill Class

class Skill : Identifiable, ObservableObject, Equatable{
    @Published var skillName:String = "";
    @Published var level:Int = 1;
    @Published var prestiege:Int = 0;
    var curXP:Double = 0.0;
    var maxXP:Double = 50.0;
    @Published var skillDesc:String;
    @Published public var skillColor:Color = Color.purple;
    @Published public var buttons: [SkillButton] = [];
    @Published private var prestCap:Int;

    //EXTRA HIDDEN CODE

}

For Reference, here is the SkillButton Class

class SkillButton : Identifiable, ObservableObject, Equatable{

    
    @Published public var xp:Double = 0;
    @Published private var buttonName:String = "";
    @Published private var uses:Int = 0;
    @Published public var buttonColor:Color = Color.pink;
    @Published private var description:String;

    enum CodingKeys: String, CodingKey {
        case buttonName, xp, uses, buttonColor, description
    }
    
    init(ButtonName buttonName:String, XpGained xp:Double, Uses uses:Int = 0, Description desc:String = "") {
        self.xp = xp;
        self.buttonName = buttonName;
        self.uses = uses;
        self.description = desc;
    }
}

I know that each of these classes need to conform to Codable, but I just couldn't find a resource to make these conform to Codable.



Solution 1:[1]

Other than not conforming the Skill and SkillButton classes to Codable, the underlying problem you have is down to the @published property wrapper, as this stops the auto-synthesis of Codable conformance.

Rather than writing out the solution, can I refer you to this Hacking with Swift link: https://www.hackingwithswift.com/books/ios-swiftui/adding-codable-conformance-for-published-properties

You will also have to conform Color to Codable yourself as (unless it's changed in recent updates?) it isn't Codable out of the box.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 flanker