2

I found this answer on how to make the enemies move towards the player. If I have one enemy on the GameScene, it works perfect. However, if I add another enemy to the scene, only one of them moves while the other is stationary.

Here is the code on how I have everything set up so far.

var player: SKSpriteNode?

var spawnZombie = SKSpriteNode()

override func didMove(to view: SKView) {
    playerTexture = SKTexture(imageNamed: "player_2")
    player = SKSpriteNode(texture: playerTexture)
    player?.name = "player"
    player?.position = (pSpawnPoint?.position)!
    player?.setScale(0.5)
    self.addChild(player!)


    randomEnemy()
    randomEnemy()
}

This is how my enemies are set up

func randomEnemy(){
    spawnPoint0 = childNode(withName: "spawnPoint_0") as? SKSpriteNode
    spawnPoint1 = childNode(withName: "spawnPoint_1") as? SKSpriteNode
    spawnPoint2 = childNode(withName: "spawnPoint_2") as? SKSpriteNode
    // Set up enemies
    enemy = SKSpriteNode(imageNamed: "enemy_2")
    enemy.name = "enemy"
    enemy.setScale(0.5)
    enemy.zPosition = 10
    enemy.physicsBody = SKPhysicsBody(rectangleOf: enemy.size)
    enemy.physicsBody?.categoryBitMask = PhysicsCatagory.Enemy
    enemy.physicsBody?.collisionBitMask = PhysicsCatagory.None
    enemy.physicsBody?.contactTestBitMask = PhysicsCatagory.Player
    enemy.physicsBody?.isDynamic = true
    enemy.physicsBody?.affectedByGravity = false

    let choice = Int(arc4random_uniform(3))
    switch choice {
    case 0:
        enemy.position = (spawnPoint0?.position)!
        self.addChild(enemy)
        break

    case 1:
        enemy.position = (spawnPoint1?.position)!
        self.addChild(enemy)
        break

    case 2:
        enemy.position = (spawnPoint2?.position)!
        self.addChild(enemy)
        break
    default:
        print("something went wrong")
    }
}

override func update(_ currentTime: TimeInterval) {

   let location = player?.position

    //Aim
    let dx = (location?.x)! - enemy.position.x
    let dy = (location?.y)! - enemy.position.y
    let angle = atan2(dy, dx)

    enemy.zRotation = angle - 3 * .pi/2

    //Seek
    let velocityX =  cos(angle) * enemySpeed
    let velocityY =  sin(angle) * enemySpeed

    enemy.position.x += velocityX
    enemy.position.y += velocityY
}

Any ideas why only one of the enemies moves whenever I run the function twice? Thanks in advance.

Ron Myschuk
  • 6,011
  • 2
  • 20
  • 32
sicvayne
  • 620
  • 1
  • 4
  • 15

1 Answers1

3

you are putting both of your enemies in the same enemy variable. so when you try to move enemy you are basically moving the last one assigned to that variable.

what you need to do is put them in an array and then move all of the enemies from the array.

let enemies = [SKSpriteNode]()


func randomEnemy() {

    //...other code blah blah blah
    enemies.append(enemy)
}

and in the update func

override func update(_ currentTime: TimeInterval) {

   let location = player?.position

    for enemy in enemies {
        //Aim
        let dx = (location?.x)! - enemy.position.x
        let dy = (location?.y)! - enemy.position.y
        let angle = atan2(dy, dx)

        enemy.zRotation = angle - 3 * .pi/2

        //Seek
        let velocityX = cos(angle) * enemySpeed
        let velocityY = sin(angle) * enemySpeed

        enemy.position.x += velocityX
        enemy.position.y += velocity
    }
}

now you probably want to look at sub classing enemy and having the move functionality in that class but that is outside the scope of your question. This should get you started.

Ron Myschuk
  • 6,011
  • 2
  • 20
  • 32
  • Had a feeling that was the issue here. As far as subclassing, I am actually considering on doing that as well. Always good to have options from other's point of view. It really helps! – sicvayne Mar 18 '18 at 06:23