我有UIView
通过播放音频文件来响应单击手势。它通过使用AVPlayer
类来完成此操作。一切都很好,有一个例外。如果用户当前正在收听音频文件,并且他们再次点击相同的UIView
,我希望音频文件返回到开头并从头开始再次播放。但是,当发生这种情况时,我得到以下控制台输出:
类AVPlayer的实例0x10ad89dd0在键时被释放 价值观察员仍在注册。观察信息是 泄露,甚至可能被错误地附着在其他物体上。
我的游戏方法中的前三行是我试图解决这个问题,但他们没有解决任何问题。音频会重新启动,但控件(播放的时间,滑块等)都会变得疯狂。我看到其他几个帖子,我仍然卡住了。任何人都可以看到我需要做些什么来解决这个问题?
- (void) playAudio : (UITapGestureRecognizer *)recognizer
{
// remove any existing observers to prevent memory leaks
[self.audioPlayer pause];
self.audioPlayer = nil;
[[NSNotificationCenter defaultCenter] removeObserver:self name:AVPlayerItemDidPlayToEndTimeNotification object:self.audioPlayer];
unsigned long buttonPressed = [self.buttonsArray indexOfObject:recognizer.view];
Sessions *session = self.sessionsList[buttonPressed];
self.mediaFile = session.media_file;
self.totalSecondsToPlay = [session.play_seconds integerValue];
[self resetAVControls];
NSString *urlString = [NSString stringWithFormat:@"%@%@", AUDIO_URL, self.mediaFile];
AVPlayer *player = [[AVPlayer alloc]initWithURL:[NSURL URLWithString:urlString]];
self.audioPlayer = player;
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(playerItemDidReachEnd:)
name:AVPlayerItemDidPlayToEndTimeNotification
object:[self.audioPlayer currentItem]];
[self.audioPlayer addObserver:self forKeyPath:@"status" options:0 context:nil];
self.isPlaying = YES;
timer = [NSTimer scheduledTimerWithTimeInterval:1.0
target:self
selector:@selector(updateProgress)
userInfo:nil
repeats:YES];
}
答案 0 :(得分:3)
您已为self.audioPlayer
注册了KeyValueObservers,但在将值设置为nil
时,您尚未将其删除。因此,在self.audioPlayer = nil;
使用[self.audioPlayer removeObserver:self forKeyPath:@"status" context:nil]
Check this如果你想了解更多关于KVO
的信息答案 1 :(得分:0)
每次将你的playerview设置为nil时,请先调用removeObserver。
实施例
[self removeObserverForStatusPlay];
playerView = nil;
在Init
之前[self removeObserverForStatusPlay];
playerView = [[AVPlayer alloc] initWithURL:url];
当removeObserverForStatusPlay方法为
时- (void)removeObserverForStatusPlay
{
@try {
[playerView removeObserver:self forKeyPath:@"status"];
} @catch(id anException) {
NSLog(@"excepcion remove observer == %@. Remove previously or never added observer.",anException);
//do nothing, obviously it wasn't attached because an exception was thrown
}
}