我正在 Swift 3 的 SpriteKit 中创建一个移动应用程序。我正在尝试创建角色必须躲避的两 block 岩石。我有随机生成 ->
func createTopRock(){
var topRockChoice = [SKTexture(image: #imageLiteral(resourceName: "rockDown")), SKTexture(image: #imageLiteral(resourceName: "rockGrassDown")), SKTexture(image: #imageLiteral(resourceName: "rockSnowDown")), SKTexture(image: #imageLiteral(resourceName: "rockIceDown"))]
let topRock = SKSpriteNode.init(texture: topRockChoice[mapChoice], size: CGSize(width: (self.scene?.size.width)! / 10, height: (self.scene?.size.height)! / 2.2))
topRock.zPosition = -9
topRock.name = "TopRock"
topRock.position = CGPoint(x: self.frame.width + topRock.size.width * 2, y: frame.maxY - topRock.frame.height / 2)
topRock.physicsBody = SKPhysicsBody(texture: topRockChoice[mapChoice], size: CGSize(width: (self.scene?.size.width)! / 10, height: (self.scene?.size.height)! / 2.2))
topRock.physicsBody?.categoryBitMask = physicsCatagory.topRock
topRock.physicsBody?.collisionBitMask = physicsCatagory.plane
topRock.physicsBody?.contactTestBitMask = physicsCatagory.plane
topRock.physicsBody?.affectedByGravity = false
topRock.physicsBody?.isDynamic = false
self.addChild(topRock)
let randomNumTop = arc4random_uniform(3) + 3
spawnDelayForeverTop = Timer.scheduledTimer(timeInterval: TimeInterval(randomNumTop), target: self, selector: #selector(self.createTopRock), userInfo: nil, repeats: false)
}
func createBtmRock(){
var btmRockChoice = [SKTexture(image: #imageLiteral(resourceName: "rock")), SKTexture(image: #imageLiteral(resourceName: "rockGrass")), SKTexture(image: #imageLiteral(resourceName: "rockSnow")), SKTexture(image: #imageLiteral(resourceName: "rockIce"))]
let btmRock = SKSpriteNode.init(texture: btmRockChoice[mapChoice], size: CGSize(width: (self.scene?.size.width)! / 10, height: (self.scene?.size.height)! / 2.2))
btmRock.zPosition = -9
btmRock.position = CGPoint(x: self.frame.width, y: frame.minY + btmRock.frame.height / 2)
btmRock.name = "BtmRock"
btmRock.physicsBody = SKPhysicsBody(texture: btmRockChoice[mapChoice], size: CGSize(width: (self.scene?.size.width)! / 10, height: (self.scene?.size.height)! / 2.2))
btmRock.physicsBody?.categoryBitMask = physicsCatagory.topRock
btmRock.physicsBody?.collisionBitMask = physicsCatagory.plane
btmRock.physicsBody?.contactTestBitMask = physicsCatagory.plane
btmRock.physicsBody?.affectedByGravity = false
btmRock.physicsBody?.isDynamic = false
self.addChild(btmRock)
let randomNumBtm = arc4random_uniform(2) + 1
spawnDelayForeverBtm = Timer.scheduledTimer(timeInterval: TimeInterval(randomNumBtm), target: self, selector: #selector(createBtmRock), userInfo: nil, repeats: false)
}
正如您从代码中看到的,一切正常。我不想做的一件事是让它像 Flappy Bird 一样,并使 btmRock
和 topRock
具有相同的位置,因此为了防止我添加了 timeIntervals
不同。这在一定程度上是有效的;但玩家仍然会遇到一些几乎不可能穿过的岩石。
我觉得我的做法是错误的,而且我不知道如何解决这个问题。我希望他们有时足够接近,很难,但并非几乎不可能。当我尝试实现一个 bool
系统时,当顶部岩石被创建并且在一定距离内时,不会创建底部岩石。我在尝试这样做时遇到的问题是,在那件事发生之后我再也没有底气了。提前致谢。
最佳答案
就我个人而言,我不会在我的 SpriteKit 游戏中使用计时器(原因你可以在 SO 中找到)。一个非常简单的解决方案可能是从 Update 函数中调用岩石的生成。
我还会创建一个基础底部岩石和基础顶部岩石,并根据需要复制它,因为动态创建物理对象可能会很昂贵(或者我会在开始时创建一个对象数组并从数组中提取)根据需要)
附注这是我即兴写下的,所以我不能保证不存在拼写错误;)
var genInterval = 4 //How many seconds between rocks on bottom or top (not between top & bottom. that will be half of this value)
var genOffset = genInterval / 2 //offset the bottom rocks half of the interval so that they do't line up
var bottomRock: SKSpriteNode! //your base bottom rock for copying
var topRock: SKSpriteNode! //your base top rock for copying
var updateTopTime: Double = 0
var updateBottomTime: Double = 0
func setupRocks() {
//create the base bottom rock
var btmRockChoice = [SKTexture(image: #imageLiteral(resourceName: "rock")), SKTexture(image: #imageLiteral(resourceName: "rockGrass")), SKTexture(image: #imageLiteral(resourceName: "rockSnow")), SKTexture(image: #imageLiteral(resourceName: "rockIce"))]
bottomRock = SKSpriteNode(texture: btmRockChoice[mapChoice], size: CGSize(width: (self.scene?.size.width)! / 10, height: (self.scene?.size.height)! / 2.2))
btmRock.zPosition = -9
btmRock.position = CGPoint(x: self.frame.width, y: frame.minY + btmRock.frame.height / 2)
btmRock.name = "BtmRock"
btmRock.physicsBody = SKPhysicsBody(texture: btmRockChoice[mapChoice], size: CGSize(width: (self.scene?.size.width)! / 10, height: (self.scene?.size.height)! / 2.2))
btmRock.physicsBody?.categoryBitMask = physicsCatagory.topRock
btmRock.physicsBody?.collisionBitMask = physicsCatagory.plane
btmRock.physicsBody?.contactTestBitMask = physicsCatagory.plane
btmRock.physicsBody?.affectedByGravity = false
btmRock.physicsBody?.isDynamic = false
//create the base top rock
var topRockChoice = [SKTexture(image: #imageLiteral(resourceName: "rockDown")), SKTexture(image: #imageLiteral(resourceName: "rockGrassDown")), SKTexture(image: #imageLiteral(resourceName: "rockSnowDown")), SKTexture(image: #imageLiteral(resourceName: "rockIceDown"))]
topRock = SKSpriteNode(texture: topRockChoice[mapChoice], size: CGSize(width: (self.scene?.size.width)! / 10, height: (self.scene?.size.height)! / 2.2))
topRock.zPosition = -9
topRock.name = "TopRock"
topRock.position = CGPoint(x: self.frame.width + topRock.size.width * 2, y: frame.maxY - topRock.frame.height / 2)
topRock.physicsBody = SKPhysicsBody(texture: topRockChoice[mapChoice], size: CGSize(width: (self.scene?.size.width)! / 10, height: (self.scene?.size.height)! / 2.2))
topRock.physicsBody?.categoryBitMask = physicsCatagory.topRock
topRock.physicsBody?.collisionBitMask = physicsCatagory.plane
topRock.physicsBody?.contactTestBitMask = physicsCatagory.plane
topRock.physicsBody?.affectedByGravity = false
topRock.physicsBody?.isDynamic = false
}
override func update(_ currentTime: CFTimeInterval) {
//optional prevents generation if game is not playing
guard gameState == .playing else { return }
if updateTopTime == 0 {
updateTopTime = currentTime
}
if updateBottomTime == 0 {
updateBottomTime = currentTime
}
if currentTime - updateBottomTime > genOffset {
createBtmRock()
genOffset = genInterval
updateBottomTime = currentTime
}
else if currentTime - updateTopTime > genInterval {
createTopRock()
updateTopTime = currentTime
}
}
func createTopRock() {
//You can make this number a class variable to increase the rate as the game progresses
let randomNum = arc4random_uniform(3)
//there is a 1 in 3 chance that this rock will get created
if randomNum == 1 {
let rock = topRock.copy as! SKSpriteNode()
self.addChild(rock)
}
}
func createBtmRock() {
//You can make this number a class variable to increase the rate as the game progresses
let randomNum = arc4random_uniform(2)
//there is a 1 in 2 chance that this rock will get created
if randomNum == 0 {
let rock = bottomRock.copy as! SKSpriteNode()
self.addChild(rock)
}
}
关于swift - 随机生成两个节点,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46120401/