我有一个名为PlayerController的View Controller,当我转到PlayerController时,它将加载一个音频文件并将其放入AVAudioPlayer,它们的播放按钮是播放AVAudioPlayer。到目前为止,一切都很好。问题是,如果我离开PlayerController并再次转到它,则仍在播放前一个AVAudioPlayer的音频,在我的viewWillAppear方法中,我有这一行来停止AVAudioPlayer的播放,但它无法正常工作,它不会停止前一个正在播放AVAudioPlayer。...我将如何完成我想做的事情?我应该在我的appDelegate文件中定义AVAudioPlayer并将其读取吗?
这是我的viewWillAppear方法:
override func viewWillAppear(_ animated: Bool)
{
super.viewWillAppear(animated)
timer = Timer.scheduledTimer(timeInterval: 0.1, target: self, selector: (#selector(PlayerController.updateTimer)), userInfo: nil, repeats: true)
if(UserDefaults.standard.integer(forKey: "nowPlayingPost") == 0)
{
UserDefaults.standard.set(self.postid, forKey: "nowPlayingPost")
audioSlider.setValue(0, animated: false)
if(self.audio != nil && (self.audio?.isPlaying)!)
{
self.audio?.stop()
}
}
else
{
audioSlider.value = Float((self.audio?.currentTime)!)
self.audioSlider.maximumValue = Float((self.audio?.duration)!)
self.postid = UserDefaults.standard.integer(forKey: "nowPlayingPost")
if(self.audio?.isPlaying)!
{
self.playButton.setTitle("Stop", for: .normal)
}
else
{
if(self.audio?.currentTime == 0)
{
self.playButton.setTitle("Play", for: .normal)
}
else
{
self.playButton.setTitle("Resume", for: .normal)
}
}
}
Alamofire.request(audioUrl!).responseData { response in
do {
self.audio = try AVAudioPlayer(data: response.data!)
self.audio?.prepareToPlay()
self.audioSlider.maximumValue = Float((self.audio?.duration)!)
}catch{
}
}
}
那么我应该在appDelegate中定义AVAudioPlayer还是使用UserDefaults或CoreData或其他东西?最佳做法是什么?
答案 0 :(得分:1)
我认为最好的解决方案是使用Singleton类来控制您的音频功能,这样,您就无需创建需要停止且不需要Notification Center复杂性的AVAudioPlayer的另一个实例。您还可以从任何视图控制器访问Singleton,并添加从Alamofire检索音频数据的方法,这样就无需通过segue传递数据或使用NSUserDefaults。
class AudioController {
static let sharedInstance = AudioController()
var nowPlayingPost: Int = 0
private init(){}
func playAudioFrom(url: URL){
// your implementation
}
// Other methods, stop, pause, etc.
}
您的View Controller中的任何地方:
AudioController.sharedInstance.playAudio(url: url)