我正在使用SpriteKit和Swift 4构建游戏,在SKNode系列中有许多自定义类。我试图使用Codable协议(假设)使游戏更容易保存。作为一个上下文,这里是游戏中主要类的高级概述:
Hero类,自定义SKSpriteNode,实现了Codable。 Hero类作为属性,具有以下形式的字典:[String:MapNode]
MapNode类,自定义SKSpriteNode,实现Codable。 MapNode类作为属性,有一个TileNodes数组,如:[TileNode]
TileNode类,自定义SKSpriteNode,实现可编码。 TileNode类只有原始属性。
我似乎能够将所有内容编码为正常,并将所有内容保存为默认值,但是当我去解码已保存的游戏时,我在MapNode类中遇到以下错误:
Thread 1: Fatal error: init(coder:) has not been implemented
在这个必需的init:
required init?(coder aDecoder: NSCoder) {
// subclass of SKNode must implement this method
fatalError("init(coder:) has not been implemented")
}
我不明白为什么这个init甚至被调用(或者为什么需要它)因为据我所知,它根本不被Codable协议使用。在这个需要init的类(MapNode)中,我还有以下Codable函数:
enum CodingKeys: String, CodingKey {
case height
case width
case tileArray
}
required init(from decoder: Decoder) throws {
let values = try decoder.container(keyedBy: CodingKeys.self)
height = try values.decode(Int.self, forKey: .height)
width = try values.decode(Int.self, forKey: .width)
let tileArrayData = try values.decode(Data.self, forKey: .tileArray)
tileArray = (NSKeyedUnarchiver.unarchiveObject(with: tileArrayData) as? [TileNode])!
self.isUserInteractionEnabled = true
self.size = CGSize(width: width, height: height)
self.name = "map"
zPosition = 5
addMapImageLayer(forMap: self)
}
func encode(to encoder: Encoder) throws {
var container = encoder.container(keyedBy: CodingKeys.self)
try container.encode(height, forKey: .height)
try container.encode(width, forKey: .width)
let tileArrayData = NSKeyedArchiver.archivedData(withRootObject: tileArray)
try container.encode(tileArrayData, forKey: .tileArray)
}
我的想法是,因为我在代码将在需要初始化和解码Codable编码数据时使用Codable函数的所有内容上实现Codable。我应该做些什么?