Reputation: 583
I have created an SKSpriteNode subclass and have attempted to instantiate it in an SKScene and set some SKSpriteNode properties with other properties that I have stored in the subclass on instantiation. Here is the class definition.
class WalkingMonster: SKSpriteNode {
var rangeOfMovement: CGFloat
var originalPosition: CGFloat
var platformNumber: Int
var imageName = "walkingAlien"
var sizes = [CGSize(width: CGFloat(30.0), height: CGFloat(30.0)), CGSize(width: CGFloat(30.0), height: CGFloat(15.0)), CGSize(width: CGFloat(30.0), height: CGFloat(7.0))]
var monsterName: String
var textureName: String
init(texture: SKTexture, color: UIColor, size: CGSize, rangeOfMovement: CGFloat, originalPosition: CGFloat, platformNumber: Int, name: String, textureName: String) {
self.rangeOfMovement = rangeOfMovement
self.originalPosition = originalPosition
self.platformNumber = platformNumber
self.monsterName = name
self.textureName = textureName
super.init(texture: texture, color: color, size: size)
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}
Here is the instantiation of the class:
var walkingMonsters = [WalkingMonster(texture: SKTexture(), color: UIColor(), size: CGSize(), rangeOfMovement: CGFloat(25.0), originalPosition: CGFloat(750.0), platformNumber: -1, name: "walkingMonster1", textureName: "walkingAlien1")]
This is how I am setting its properties in the SKScene within didMoveToView():
for monster in walkingMonsters {
let texture = SKTexture(imageNamed: monster.textureName)
monster.texture = texture
monster.size = monster.sizes[0]
monster.position.x = monster.originalPosition
//If it is supposed to sit on the ground
if monster.platformNumber < 0 {
monster.position.y = self.groundHeight + super.groundBlockSize.height / 2 + monster.size.height / 2
}
monster.physicsBody?.categoryBitMask = physicsBitMasks.walkingEnemy
monster.physicsBody?.contactTestBitMask = physicsBitMasks.ground | physicsBitMasks.player | physicsBitMasks.aerialBlock
monster.physicsBody?.contactTestBitMask = physicsBitMasks.ground | physicsBitMasks.player | physicsBitMasks.aerialBlock
monster.physicsBody?.dynamic = true
monster.physicsBody?.affectedByGravity = true
self.addChild(monster)
}
}
At runtime there is a monster that spawns, but he (or at least his texture) appears to be off the ground a little. When the player (who has categoryBitMask of .player and whose contact and collision bit masks include .walkingEnemy) walks into him, nothing happens to the movement of the main character and the walkingMonster (walkingMonsters[0]) does not move either. I am not sure if there is some small thing I am missing syntactically or if there is a larger blocker.
My other method of doing this, which I have already implemented successfully, was to store those member variables of what should stylistically be a subclass of SKSpriteNode in corresponding parameter vectors, then set them after using the SKSpriteNode convenience initializer SKSpriteNode(imageNamed: "whatever"). I think subclassing is the way to go however.
Upvotes: 0
Views: 53
Reputation: 583
The issue was that I was not initializing the physicsbody for each monster in the loop.
for monster in walkingMonsters {
let body = SKPhysicsBody(rectangleOfSize: monster.sizes[0])
monster.physicsBody = body
//rest of setting comes here
}
Upvotes: 0