2013-10-23 25 views
2
-(void) setupAVPlayerForURL:(NSString *)url 
{ 
    [appdelegate.sharedplayer stop]; 

    appdelegate.sharedplayer=[[AVAudioPlayer alloc] initWithContentsOfURL:url1 error:NULL]; 
    [[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayback error:nil]; 
    [[AVAudioSession sharedInstance] setActive: YES error: nil]; 
    [[UIApplication sharedApplication] beginReceivingRemoteControlEvents]; 

    [appdelegate.sharedplayer setVolume:appdelegate.volumeDelegate]; 

    [appdelegate.sharedplayer play]; 
    self.seekBarSlider.minimumValue = 0.0f; 
    self.seekBarSlider.maximumValue = appdelegate.sharedplayer.duration; 
    self.isPlaying=YES; 
    appdelegate.sharedplayer.delegate=self; 

    [self loadAlbumArt]; 
    [appdelegate.sharedplayer addObserver:self forKeyPath:@"status" options:0 context:nil]; 
} 

每當我運行這個程序,除了我第一次得到這個日誌消息,但應用程序不崩潰AVAudioPlayer被釋放,而鍵值觀察家仍用它

An instance 0xc1693d0 of class AVAudioPlayer was deallocated while key value observers were still registered with it. 
Observation info was leaked, and may even become mistakenly attached to some other object. Set a breakpoint on NSKVODeallocateBreak to stop here in the debugger. 

下面是當前觀測信息註冊:

<NSKeyValueObservationInfo 0xc194d90> (
<NSKeyValueObservance 0xc194e40: Observer: 0xc1697d0, Key path: 
status, Options: <New: NO, Old: NO, Prior: NO>   Context: 0x0, 
Property: 0xc194d70>) 

我在做什麼錯?

回答

6

您必須從觀察者刪除self。當您撥打-stop時,AVAudioPlayer的實例將被釋放(您創建一個新實例)。但是你試圖繼續保留它的價值。

因此,您嘗試觀察內存中不再存在的實例。

試試這個:

- (void)setupAVPlayerForURL:(NSURL *)url { 
    [[appdelegate sharedplayer] removeObserver:self]; 
    [[appdelegate sharedplayer] stop]; 

    // and so on 
} 

您的應用程序不崩潰,因爲你訪問的釋放的實例。 相反,系統會「崩潰」你的應用程序,因爲被觀察對象的內存地址(然後被釋放)可能稍後會指向其他對象,這將導致錯誤的觀察消息被派發給觀察者。

1

設置avPlayerLayer到零去除觀察者

[avPlayerLayer removeObserver:self forKeyPath:@"readyForDisplay"]; 
avPlayerLayer=nil; 

在viewdisappear檢查avPlayerLayer不爲零然後取出觀察

if (avPlayerLayer) 
{ 
    [avPlayerLayer removeObserver:self forKeyPath:@"readyForDisplay"]; 
} 
相關問題