Looping a video with AVFoundation AVPlayer?

avfoundation, avplayer, ios, objective-c, swift

Solution

You can get a Notification when the player ends. Check `AVPlayerItemDidPlayToEndTimeNotification`

When setting up the player:

ObjC

  avPlayer.actionAtItemEnd = AVPlayerActionAtItemEndNone; 

  [[NSNotificationCenter defaultCenter] addObserver:self
                                           selector:@selector(playerItemDidReachEnd:)
                                               name:AVPlayerItemDidPlayToEndTimeNotification
                                             object:[avPlayer currentItem]];

this will prevent the player to pause at the end.

in the notification:

- (void)playerItemDidReachEnd:(NSNotification *)notification {
    AVPlayerItem *p = [notification object];
    [p seekToTime:kCMTimeZero];
}

this will rewind the movie.

Don't forget un unregister the notification when releasing the player.

Swift

avPlayer?.actionAtItemEnd = .none

NotificationCenter.default.addObserver(self,
                                       selector: #selector(playerItemDidReachEnd(notification:)),
                                       name: .AVPlayerItemDidPlayToEndTime,
                                       object: avPlayer?.currentItem)

@objc func playerItemDidReachEnd(notification: Notification) {
    if let playerItem = notification.object as? AVPlayerItem {
        playerItem.seek(to: kCMTimeZero)
    }
}

Swift 4+

@objc func playerItemDidReachEnd(notification: Notification) {
    if let playerItem = notification.object as? AVPlayerItem {
        playerItem.seek(to: CMTime.zero, completionHandler: nil)
    }
}

Problem

Is there a relatively easy way of looping a video in AVFoundation? I've created my AVPlayer and AVPlayerLayer like so: ``` avPlayer = [[AVPlayer playerWithURL:videoUrl] retain]; avPlayerLayer = [[AVPlayerLayer playerLayerWithPlayer:avPlayer] retain]; avPlayerLayer.frame = contentView.layer.bounds; [contentView.layer addSublayer: avPlayerLayer]; ``` and then I play my video with: ``` [avPlayer play]; ``` The video plays fine but stops at the end. With the MPMoviePlayerController all you have to do is set its `repeatMode` property to the right value. There doesn't appear to be a similar property on AVPlayer. There also doesn't seem to be a callback that will tell me when the movie has finished so I can seek to the beginning and play it again. I'm not using MPMoviePlayerController because it has some serious limitations. I want to be able to play back multiple video streams at once.

Original source

Related problems