iOS - 如何获得AVPlayer的可播放持续时间

时间:2011-07-25 11:25:16

标签: ios xcode avplayer mpmovieplayer

MPMoviePlayerController有一个名为playableDuration的属性。

  

playableDuration 当前可播放内容的数量(只读)。

     

@property(nonatomic,readonly)NSTimeInterval playableDuration

     

对于逐步下载的网络内容,此属性会反映出来   现在可以播放的内容量。

AVPlayer有类似的东西吗? 我在Apple Docs或Google中找不到任何东西(在Stackoverflow.com上都没有找到)

提前致谢。

5 个答案:

答案 0 :(得分:15)

playableDuration可以按照以下步骤粗略实现:

- (NSTimeInterval) playableDuration
{
//  use loadedTimeRanges to compute playableDuration.
AVPlayerItem * item = _moviePlayer.currentItem;

if (item.status == AVPlayerItemStatusReadyToPlay) {
    NSArray * timeRangeArray = item.loadedTimeRanges;

    CMTimeRange aTimeRange = [[timeRangeArray objectAtIndex:0] CMTimeRangeValue];

    double startTime = CMTimeGetSeconds(aTimeRange.start);
    double loadedDuration = CMTimeGetSeconds(aTimeRange.duration);

    // FIXME: shoule we sum up all sections to have a total playable duration,
    // or we just use first section as whole?

    NSLog(@"get time range, its start is %f seconds, its duration is %f seconds.", startTime, loadedDuration);


    return (NSTimeInterval)(startTime + loadedDuration);
}
else
{
    return(CMTimeGetSeconds(kCMTimeInvalid));
}
}

_moviePlayer是您的AVPlayer实例,通过检查AVPlayerItem的loadedTimeRanges,您可以计算估计的playableDuration。

对于只有1秒的视频,您可以使用此程序;但对于多节视频,您可能需要检查loadedTimeRagnes数组中的所有时间范围,以获得正确的答案。

答案 1 :(得分:6)

你需要的只是

self.player.currentItem.asset.duration

简直是最好的

答案 2 :(得分:4)

以约翰的答案为基础......

这是Apple玩家的明显默认行为:“显示包含当前时间的可播放范围的最长时间”

- (NSTimeInterval)currentItemPlayableDuration{

//  use loadedTimeRanges to compute playableDuration.
AVPlayerItem * item = self.audioPlayer.currentItem;

if (item.status == AVPlayerItemStatusReadyToPlay) {
    NSArray * timeRangeArray = item.loadedTimeRanges;

    CMTime currentTime = self.audioPlayer.currentTime;

    __block CMTimeRange aTimeRange;

    [timeRangeArray enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {

       aTimeRange = [[timeRangeArray objectAtIndex:0] CMTimeRangeValue];

        if(CMTimeRangeContainsTime(aTimeRange, currentTime))
            *stop = YES;

    }];

    CMTime maxTime = CMTimeRangeGetEnd(aTimeRange);

    return CMTimeGetSeconds(maxTime);
}
else
{
    return(CMTimeGetSeconds(kCMTimeInvalid));
}

}

答案 3 :(得分:2)

您必须检测AVPlayer何时准备好播放您的媒体文件。 如果您不知道如何做,请告诉我。

但是,加载媒体文件后,您可以使用此方法:

#import <AVFoundation/AVFoundation.h>

/**
 * Get the duration for the currently set AVPlayer's item. 
 */
- (CMTime)playerItemDuration {
    AVPlayerItem *playerItem = [mPlayer currentItem];
    if (playerItem.status == AVPlayerItemStatusReadyToPlay) {
        return [[playerItem asset] duration];
    }
    return(kCMTimeInvalid);
}

当您使用此方法时,了解(因为您正在流式传输内容)重要的是长度值可能无效或其他。所以在使用它进行处理之前必须先检查一下。

CMTime playerDuration = [self playerItemDuration];
if (CMTIME_IS_INVALID(playerDuration)) {
    return;
}
double duration = CMTimeGetSeconds(playerDuration);

答案 4 :(得分:1)

关闭可播放持续时间的快速版本:

var playableDuration: TimeInterval? {
    guard let currentItem = currentItem else { return nil }
    guard currentItem.status == .readyToPlay else { return nil }

    let timeRangeArray = currentItem.loadedTimeRanges
    let currentTime = self.currentTime()

    for value in timeRangeArray {
        let timeRange = value.timeRangeValue
        if CMTimeRangeContainsTime(timeRange, currentTime) {
            return CMTimeGetSeconds(CMTimeRangeGetEnd(timeRange))
        }
    }

    guard let timeRange = timeRangeArray.first?.timeRangeValue else { return 0}

    let startTime = CMTimeGetSeconds(timeRange.start)
    let loadedDuration = CMTimeGetSeconds(timeRange.duration)
    return startTime + loadedDuration
}