随机生成SKSpriteNode对象

问题描述 投票:-1回答:1

我正在制作一个游戏,我想在随机时间产生障碍物。障碍将与玩家联系。

这里是我的代码:

var obstacle : SKSpriteNode?

func createObstacles() {
let obstaclesArray = ["obstacle_1", "obstacle_2", "obstacle_3", "obstacle_4", "obstacle_5"]
let randomObs = obstaclesArray.randomElement()
let selectedTexture = SKTexture(imageNamed: randomObs!)
obstacle = SKSpriteNode(imageNamed: randomObs!)
obstacle?.physicsBody = SKPhysicsBody(texture: selectedTexture, size: selectedTexture.size())
obstacle?.position = CGPoint(x: scene!.size.width/2 + selectedTexture.size().width, y: -120)
obstacle?.zPosition = -15
if let obs = obstacle?.physicsBody {
obs.affectedByGravity = true
obs.allowsRotation = false
obs.isDynamic = true
obs.restitution = 0
obs.categoryBitMask = obstacleCategory
obs.collisionBitMask = floorCategory
obs.contactTestBitMask = heroCategory
}
addChild(obstacle!)
}

func spawnObstacles() {
let wait = SKAction.wait(forDuration: 1, withRange: 0.4)
let spawn = SKAction.run {
createObstacles()
}
let moveLeft = SKAction.moveBy(x: -scene!.size.width - obstacle.size.width - 10, y: 0, duration: 2)
let sequence = SKAction.sequence([wait, spawn, moveLeft, SKAction.removeFromParent()])
self.run(SKAction.repeatForever(sequence))
}

我读了一些类似的问题,但响应是我的相同代码,但它不起作用。 Spawning a Spritekit node at a random time

我也尝试过其他方式:

var randDelay = Double.random(in: 0.7 ..< 1.4)
DispatchQueue.main.asyncAfter(deadline: randDelay, execute: {
    if self.canCreateObstacle == true {
    self.spawnObstacle()
    }})

但它不起作用,每次我重新启动游戏时,似乎函数被调用两次,如果我第三次重启游戏,它被调用3次,依此类推。

任何人都有一个良好而干净的解决方案来随机产生对象?

swift sprite-kit skspritenode skaction
1个回答
0
投票

不要使用DispatchQueue像以前一样使用wait(forDuration:withRange:)设置重复的连续动作。

https://developer.apple.com/documentation/spritekit/skaction/1417760-wait

首先,创建用于生成障碍物的通用节点,然后将此通用节点附加到场景中。 最后,将重复的顺序操作分配给此节点。热潮,你完成了。

您希望将其分配给随机节点的原因是因为您希望能够为游戏提供停止生成障碍的机会,并且您需要更改速度属性以使节点生成节点更快或更慢。

您还想要从移动/销毁中分离产卵/等待,因为截至目前,您的代码很混乱。你是说将场景向左移动2秒,然后等待一段随机的时间来产生下一个敌人,但我认为你试图在一个时间间隔内产生敌人并将敌人移到左边。

你的场景代码看起来应该是这样的

class GameScene : SKScene{
    let obstacleGenerator = SKNode()
    func didMove(to: view){


        let wait = SKAction.wait(forDuration: 1, withRange: 0.4)
        let spawn = SKAction.run({createObstacles()})

        let sequence = SKAction.sequence([wait, spawn])
        obstacleGenerator.run(SKAction.repeatForever(sequence))
        addChild(obstacleGenerator)

    }

    func createObstacles() {
        let obstaclesArray = ["obstacle_1", "obstacle_2", "obstacle_3", "obstacle_4", "obstacle_5"]
        let randomObs = obstaclesArray.randomElement()
        let selectedTexture = SKTexture(imageNamed: randomObs!)
        obstacle = SKSpriteNode(imageNamed: randomObs!)

        obstacle.position = CGPoint(x: scene!.size.width/2 + selectedTexture.size().width, y: -120)
        obstacle.zPosition = -15
        let body = SKPhysicsBody(texture: selectedTexture, size: selectedTexture.size())
        body.affectedByGravity = true
        body.allowsRotation = false
        body.isDynamic = true
        body.restitution = 0
        body.categoryBitMask = obstacleCategory
        body.collisionBitMask = floorCategory
        body.contactTestBitMask = heroCategory
        obstacle.physicsBody = body
        addChild(obstacle!)
        let moveLeft = SKAction.moveBy(x: -scene!.size.width - obstacle.size.width - 10, y: 0, duration: 2)
        let seq = SKAction.sequence([moveLeft,SKAction.removeFromParent()])
        obstacle.run(seq)
    }
}

现在,每次重置时你的产卵都会增加,你永远不会发布你的重置方式。我将假设您在重置时从不删除上一个操作,这就是您的费率增加的原因。在进行重置时,最好只创建一个新的GameScene实例。

© www.soinside.com 2019 - 2024. All rights reserved.