Swift - Must call a designated initializer of the superclass SKSpriteNode error
Asked Answered
P

2

73

This code worked on first XCode 6 Beta, but on latest Beta it's not working and gives such errors Must call a designated initializer of the superclass SKSpriteNode:

import SpriteKit

class Creature: SKSpriteNode {
  var isAlive:Bool = false {
    didSet {
        self.hidden = !isAlive
    }
  }
  var livingNeighbours:Int = 0

  init() {
    // throws: must call a designated initializer of the superclass SKSpriteNode
    super.init(imageNamed:"bubble") 
    self.hidden = true
  }

  init(texture: SKTexture!) {
    // throws: must call a designated initializer of the superclass SKSpriteNode
    super.init(texture: texture)
  }

  init(texture: SKTexture!, color: UIColor!, size: CGSize) {
    super.init(texture: texture, color: color, size: size)
  }
}

and that's how this class is initialiazed:

let creature = Creature()
creature.anchorPoint = CGPoint(x: 0, y: 0)
creature.position = CGPoint(x: Int(posX), y: Int(posY))
self.addChild(creature)

I'm stuck with it.. what will be the easiest fix?

Patterman answered 6/8, 2014 at 15:25 Comment(0)
S
100

init(texture: SKTexture!, color: UIColor!, size: CGSize) is the only designated initializer in the SKSpriteNode class, the rest are all convenience initializers, so you can't call super on them. Change your code to this:

class Creature: SKSpriteNode {
    var isAlive:Bool = false {
        didSet {
            self.hidden = !isAlive
        }
    }
    var livingNeighbours:Int = 0

    init() {
        // super.init(imageNamed:"bubble") You can't do this because you are not calling a designated initializer.
        let texture = SKTexture(imageNamed: "bubble")
        super.init(texture: texture, color: UIColor.clearColor(), size: texture.size())
        self.hidden = true
    }

    init(texture: SKTexture!) {
        //super.init(texture: texture) You can't do this because you are not calling a designated initializer.
        super.init(texture: texture, color: UIColor.clearColor(), size: texture.size())
    }

    init(texture: SKTexture!, color: UIColor!, size: CGSize) {
        super.init(texture: texture, color: color, size: size)
    }
}

Furthermore I would consolidate all of these into a single initializer.

Sinister answered 6/8, 2014 at 22:7 Comment(6)
I managed to fix this with overriding convenience init - https://mcmap.net/q/272728/-swift-must-call-a-designated-initializer-of-the-superclass-skspritenode-errorPatterman
@grfs: Very helpful answer, but I'm curious: where is it documented that this is the only designated initializer for SKSpriteNode?Beguin
@Beguin developer.apple.com/library/prerelease/ios/documentation/…:Sinister
@Beguin If you look at how the initializers are declared, you will see the convenience initializers are marked with the convenience keyword, and the designated initializers are not. It's not that clear because you need to click on every initializer and look at the way it's declared. Hopefully they develop a better way of showing it in the future.Sinister
I wish I could up vote this twice as this answer just made the correlation between convenience initializers and super inits click for me. Thanks @Epic ByteStreamlet
Good answer but assuming you want it to work like the existing convenience initializers, then the color parameter should default to SKColor.whiteColor() not UIColor.clearColor().Descry
P
14

Crazy stuff.. I don't fully understand how I managed to fix it.. but this works:

convenience init() {
    self.init(imageNamed:"bubble")
    self.hidden = true
}

init(texture: SKTexture!, color: UIColor!, size: CGSize) {
    super.init(texture: texture, color: color, size: size)
}

add convenience to init and remove init(texture: SKTexture!)

Patterman answered 6/8, 2014 at 15:43 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.