您好我试图在AVPlayerItem
中观察AVPlayer
和UIViewController
。
但是我在做这件事时遇到了一些麻烦。我已经搜索了很多并找到了很多例子,但这些都不适合我。
这是我的ViewController
:
class VideoAudioViewController: UIViewController {
var audioPlayer: AVPlayer!
var playerItem: AVPlayerItem!
private var audio: Audio
private let ITEM_STATUS_PATH = #keyPath(AVPlayerItem.status)
private let PLAYER_STATUS_PATH = #keyPath(AVPlayer.status)
private let PLAYER_RATE_PATH = #keyPath(AVPlayer.rate)
init(for audio: Audio) {
self.audio = audio
super.init(nibName: nil, bundle: nil)
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
override func viewDidLoad() {
super.viewDidLoad()
// Play audio
playerItem = AVPlayerItem(url: audio.url)
playerItem.addObserver(self, forKeyPath: ITEM_STATUS_PATH, options: [.old, .new], context: nil)
audioPlayer = AVPlayer(playerItem: playerItem)
audioPlayer!.play()
// audioPlayer!.
var audioSession = AVAudioSession.sharedInstance()
do {
try audioSession.setCategory(AVAudioSessionCategoryPlayback)
} catch {
print("error")
}
NotificationCenter.default.addObserver(
self, selector: #selector(handleInterruption), name: .AVAudioSessionInterruption, object: audioSession)
audioPlayer.addObserver(self, forKeyPath: PLAYER_STATUS_PATH, options: [.old, .new], context: nil)
audioPlayer.addObserver(self, forKeyPath: PLAYER_RATE_PATH, options: [.old, .new], context: nil)
}
override func observeValue(forKeyPath keyPath: String?, of object: Any?,
change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) {
if keyPath == "status" {
switch (audioPlayer.status) {
case AVPlayerStatus.readyToPlay:
print("player status ready to play")
audioPlayer.play()
break
case AVPlayerStatus.failed:
print("player status failed")
break
default:
break
}
return
} else if keyPath == "rate" {
if audioPlayer.rate != 0 {
playPauseButton.setImage(#imageLiteral(resourceName: "ic_pause_circle_outline_white"), for: .normal)
} else {
playPauseButton.setImage(#imageLiteral(resourceName: "ic_play_circle_outline_white"), for: .normal)
}
} else if keyPath == "status" {
switch (playerItem.status) {
case AVPlayerItemStatus.readyToPlay:
print("player item ready to play")
break
case AVPlayerItemStatus.failed:
print("player item failed")
break
default:
break
}
return
}
super.observeValue(forKeyPath: keyPath, of: object, change: change, context: context)
}
// MARK: - AVAudioPlayer delegate
func handleInterruption(_ notification: Notification) {
guard let info = notification.userInfo,
let typeValue = info[AVAudioSessionInterruptionTypeKey] as? UInt,
let type = AVAudioSessionInterruptionType(rawValue: typeValue) else {
return
}
if type == .began {
playPauseButton.setImage(#imageLiteral(resourceName: "ic_play_circle_outline_white"), for: .normal)
}
else if type == .ended {
// guard let optionsValue =
// userInfo[AVAudioSessionInterruptionOptionKey] as? UInt else {
// return
// }
// let options = AVAudioSessionInterruptionOptions(rawValue: optionsValue)
// if options.contains(.shouldResume) {
// Interruption Ended - playback should resume
audioPlayer?.play()
// }
}
}
}
我的问题是:
Terminati
ng app due to uncaught exception 'NSInternalInconsistencyException', reason: '<TheSimpleClub_Nachhilfe.VideoAudioViewController: 0x7fa6ee2b0c10>: An -observeValueForKeyPath:ofObject:change:context: message was received but not handled.
Key path: rate
Observed object: <AVPlayer: 0x60000021c8c0>
Change: {
kind = 1;
new = 1;
old = 1;
}
Context: 0
x0'
此行中出现错误:
super.observeValue(forKeyPath: keyPath, of: object, change: change, context: context)
我该怎么做才能解决这个问题?