2016-08-23 51 views
1

我该如何捕捉瞬间SKScene变为暂停或audioEngine停止了?我有两个SKScenes:GameScene和EndScene,我在游戏中使用GameScene的audioEngine属性(此属性包含AVAudioEngine对象)播放声音。当比赛结束时,从GameScene场景变化EndScene:我该如何捕捉瞬间SKScene变成暂停或audioEngine停止了?

 self.view?.presentScene(EndScene()) 

在此之后,当用户触摸«重启»,比赛重新开始,场景变化从EndScene回GameScene:

 self.view?.presentScene(GameScene(), transition: SKTransition.crossFadeWithDuration(1.0)) 

当场景从EndScene变为GameScene时,GameScene暂停了一秒(因为参数值为SKTransition.crossFadeWithDuration(1.0))。由于GameScene暂停,audioEngine也停止了。此后,GameScene会自动启动,但audioEngine不会启动并停止。然后,游戏在第一次尝试播放声音时崩溃,这很明显:因为audioEngine已停止。 为了避免这种情况,我需要在audioEngine停止后启动它,但是有一个问题需要解决:GameScene的didMoveToView()中试图捕获它,但GameScene没有暂停,它暂停了之后,didMoveToView()已经完成。 这是我的问题: 我该如何捕捉瞬间SKScene变成暂停或audioEngine停止了?有没有适合这种情况的通知或事件处理程序,也许?

回答

0

使用update函数来检查每次调用帧(每秒60次)。在它里面,放一个条件语句(如果,等等)来检查你想要的条件。例如,用此来检查如果场景暂停:

override func update(currentTime: CFTimeInterval) { 

if isPaused == true { 

// Code to run when scene is paused 

     } 

} 

请注意,这是斯威夫特3和更低的版本isPaused只是paused

另一个选择可能是使用循环像whiledo-while连续的条件检查

+0

在问我的问题之前,我想过使用update()事件来捕捉这个,但在我看来这是相当粗糙的方式。使用do-while的方式(在didMoveToView结尾,正如我的建议你的意思)看起来更有效率,谢谢你的建议。但是,最后,我决定在声音播放之前每次检查audioEngine状态,在功能播放声音。我认为这种方法合理高效。我已经发布它作为下面我自己的问题的答案。 –

+0

好的。它取决于你,因为有很多方法可以做到这一点。 – Nik

1

最后,我已经降至试图找到一些合适的通知或事件,并决定每次的Audioengine检查状态声音播放之前,在功能上播放声音。我认为这种方式是合理的效率:

func playSound(soundType: Sounds) { 

    if !audioEngine.running { 
     do { 
      try audioEngine.start() 
     } catch { 
     } 
    } 

    var soundNode = SKAudioNode() 
    var waitingDuration = Double() 

    switch soundType { 
    case .enemyDestroyed: 
     soundNode = SKAudioNode(fileNamed: "Blip001.wav") 
     waitingDuration = 3 
    case .playerDestroyed: 
     soundNode = SKAudioNode(fileNamed: "Noise002.wav") 
     waitingDuration = 5 
    } 

    soundNode.autoplayLooped = false 

    self.addChild(soundNode) 
    soundNode.runAction(SKAction.changeVolumeTo(0.5, duration: 0)) 
    soundNode.runAction(SKAction.changeReverbTo(0.5, duration: 0)) 
    soundNode.runAction(SKAction.sequence([SKAction.play(), SKAction.waitForDuration(waitingDuration), SKAction.removeFromParent()])) 

}