无法删除或停止AVPlayer

13

每当点击链接时,我会将AVPlayer加载到一个新视图上。

-(void)createAndConfigurePlayerWithURL:(NSURL *)movieURL sourceType:(MPMovieSourceType)sourceType {
self.playerItem = [AVPlayerItem playerItemWithURL:movieURL];
customControlOverlay = [[AFDetailViewController alloc] initWithNibName:@"AFMovieScrubControl" bundle:nil];
backgroundWindow = [[UIApplication sharedApplication] keyWindow];
[customControlOverlay.view setFrame:backgroundWindow.frame];
[backgroundWindow addSubview:customControlOverlay.view];

playerLayer = [AVPlayerLayer playerLayerWithPlayer:[AVPlayer playerWithPlayerItem:playerItem]];
[playerLayer.player play];
playerLayer.frame = customControlOverlay.view.frame;
[customControlOverlay.view.layer addSublayer:playerLayer]; 
}

上面的代码将AVPlayer添加到我的应用程序中,并且运行良好。我在自定义控制覆盖nib中有一个切换开关,应该移除视图并停止AVPlayer的播放。

-(IBAction)toggleQuality:(id)sender {
if (qualityToggle.selectedSegmentIndex == 0) {
    NSLog(@"HD");
    [playerLayer.player pause];
    [self.view removeFromSuperview];

} else if (qualityToggle.selectedSegmentIndex == 1) {
    NSLog(@"SD");
}
}

视图已正确移除,但播放器仍在后台播放。经过测试,播放器不会对toggleQuality方法中的任何代码作出响应,但我在那里检查的字符串会被记录。

你有什么想法我做错了什么吗?


2
在将其从父视图中移除之前,请使用playerLayer.player = nil; - Paresh Navadiya
即使我这样做,声音仍然在播放。 - AFraser
如果您按照相反的顺序进行操作(先删除再设置为 nil),会怎么样? - Squatch
尝试更改顺序,但仍无法移除。 - AFraser
1
使用 playerLayer.player = nil; 在从 superview 中移除之前,这应该是正确的答案。下面的答案对我没有起作用。 - Yoga
显示剩余2条评论
2个回答

27

我知道这是一个老问题,但它可能会对某个人有所帮助。

由于 playerLayer 被添加为一个sublayer而不是subview,因此只需要从其超级图层(而不是父视图)中删除它并将播放器设置为 nil,就像这样:

/* not sure if the pause/remove order would matter */
[playerLayer.player pause];
// uncomment if the player not needed anymore
// playerLayer.player = nil;
[playerLayer removeFromSuperlayer];

1
救了我的命,谢谢。 - Duck
1
不好意思,很久没联系了。但是,下面的代码应该放在哪里?是在 viewDidDisappear: 还是 viewWillDisappear:?我两个地方都试过了,但都没有用...你能帮我吗?提前感谢你。 - Calios
@Lilac,你最终找到把这段代码放在哪里了吗? - Jay Q.
1
@JayQ。恐怕我没有使用这种方法来解决我的问题。它对我不起作用。 - Calios

2

以下是 Swift 语言的答案。

如下方评论中 @Paresh Navadiya 和 @Yoga 所说,必须将 playerLayer 的 player 设置为 nil。 playerLayer?.player = nil

在 viewWillDisappear 中添加此代码:

override func viewWillDisappear(_ animated: Bool) {
        super.viewWillDisappear(animated)

        player?.pause() // 1. pause the player to stop it
        playerLayer?.player = nil // 2. set the playerLayer's player to nil
        playerLayer?.removeFromSuperlayer() // 3 remove the playerLayer from its superLayer
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接