美文网首页iOS Developer程序员iOS精品文章
AVFoundation视频处理的时间CMTime

AVFoundation视频处理的时间CMTime

作者: 竹与豆 | 来源:发表于2018-06-19 10:23 被阅读71次

    一、CMTime

    Core Media定义的一种时间数据类型

    typedef struct
    {
        CMTimeValue value;  //64位有符号整型变量,作为分子
        CMTimeScale timescale;   //32位有符号整型变量,作为分母
        // value/timescale = 对应时间-秒
        CMTimeFlags flags; //位掩码,表示时间的指定状态,比如判定诗句是否有效、不确定或是是否出现舍入等
        CMTimeEpoch epoch;      
    } CMTime;
    

    1、创建CMTime

    • 1、CMTimeMake()
      CMTime CMTimeMake( int64_t value,int32_t timescale)

    创建一个代表3秒的CMTime表达式(value/timescale):

    CMTime ts1 = CMTimeMake(3, 1);
    CMTime ts2 = CMTimeMake(1800, 600);
    CMTime ts3 = CMTimeMake(132300, 44100);
    
    //打印时间结果
    CMTimeShow(ts1);
    CMTimeShow(ts2);
    CMTimeShow(ts3);
    
    //打印结果
    {3/1 = 3.000}
    {1800/600 = 3.000}
    {132300/44100 = 3.000}
    

    在处理视频内容时常见的时间刻度为600,这是大部分常用视频帧率24FPS、25FPS、30FPS的公倍数。音频常见的时间刻度就是采样率,如44.1kHz(44100)、48kHz(48000)。

    • 2、CMTimeMakeWithSeconds()

    CMTime CMTimeMakeWithSeconds( Float64 seconds, int32_t preferredTimescale)

    CMTime t = CMTimeMakeWithSeconds(5, 1); // 5 seconds
    
    CMTimeShow(t);
    //{5/1 = 5.000}
    
    • 3、CMTimeMakeFromDictionary
    NSDictionary *timeData = @{(id)kCMTimeValueKey : @2,
                               (id)kCMTimeScaleKey : @1,
                               (id)kCMTimeFlagsKey : @1,
                               (id)kCMTimeEpochKey : @0};
    CMTime t = CMTimeMakeFromDictionary((__bridge CFDictionaryRef)timeData); 
    
    CMTimeShow(t);
    //{2/1 = 2.000}
       
    

    2、CMTime运算

    • 1、加减
    CMTime ts1 = CMTimeMake(3, 1);
    CMTime ts2 = CMTimeMake(5, 2);
        
    CMTime result;
    result = CMTimeAdd(ts1, ts2);
    CMTimeShow(result);
    //{11/2 = 5.500}
        
    result = CMTimeSubtract(ts1, ts2);
    CMTimeShow(result);
    //{1/2 = 0.500}
    
    • 2、比较
    CMTime t1 = CMTimeMake(300, 100); // 3 seconds
    CMTime t2 = CMTimeMakeWithSeconds(5, 1); // 5 seconds
    

    CMTimeCompare()

    int32_t r  = CMTimeCompare(t1, t2);
    NSLog(@"compare: %d",r);
    //t1 < t2   => -1
    //t1 == t2  => 0
    //t1 > ts   => 1
    

    CMTIME_COMPARE_INLINE()

    NSLog(@"t1 > t2 => %@",CMTIME_COMPARE_INLINE(t1, >, t2) ? @"YES":@"NO");
    // t1 > t2 => NO
    
    • 3、验证CMTIME_IS_VALID()
    NSLog(@"ti is valid :%@",CMTIME_IS_VALID(t1) ? @"YES":@"NO");
    // ti is valid :YES
    
    

    3、CMTime转换为秒

    Float64 CMTimeGetSeconds( CMTime time)

    CMTime t1 = CMTimeMake(3001, 100);
    NSLog(@"second : %f",CMTimeGetSeconds(t1));
    //second : 30.010000
    

    4、转换为对象NSValue

    + (NSValue *)valueWithCMTime:(CMTime)time;

    CMTime structTime = CMTimeMake(1, 3);
    
    NSValue *valueTime = [NSValue valueWithCMTime:structTime];
    NSLog(@"%@", valueTime);
    //CMTime: {1/3 = 0.333}
    
    structTime = [valueTime CMTimeValue];
    CMTimeShow(structTime);
    //{1/3 = 0.333}
    

    5、转换字典NSDictionary

     CMTime structTime = CMTimeMake(1, 3);
    NSDictionary *timeDict = CFBridgingRelease(CMTimeCopyAsDictionary(structTime, NULL));
    NSLog(@"%@", timeDict);
    
    structTime = CMTimeMakeFromDictionary((__bridge CFDictionaryRef)(timeDict));
    CMTimeShow(structTime);
    
    /*
     {
        epoch = 0;
        flags = 1;
        timescale = 3;
        value = 1;
    }
    {1/3 = 0.333}
    
    */
    
    

    二、CMTimeRange

    时间范围的数据类型:CMTimeRange,由两个CMTime值组成,第一个定义时间范围的起点,第二个定义时间范围的持续时间。

    typedef struct
    {
        CMTime          start;
        CMTime          duration;
    } CMTimeRange;
    

    1、创建

    • 1、CMTimeRangeMake()

    CMTimeRange CMTimeRangeMake( CMTime start, CMTime duration)
    根据开始时间点与持续时间确定时间范围。

    //创建一个时间范围,从时间轴的5秒位置开始,持续时长5秒
    CMTime duration = CMTimeMake(5, 1);
    CMTimeRange range = CMTimeRangeMake(duration, duration);
    CMTimeRangeShow(range);
    
    //{{5/1 = 5.000}, {5/1 = 5.000}}
    
    • 2、CMTimeRangeFromTimeToTime()

    CMTimeRange CMTimeRangeFromTimeToTime( CMTime start, CMTime end )
    根据起始时间点和终止时间点,确定时间范围。

    CMTime beginTime = CMTimeMake(5, 1);
    CMTime endTime = CMTimeMake(12, 1);
    CMTimeRange rangeTime = CMTimeRangeFromTimeToTime(beginTime, endTime);
    CMTimeRangeShow(rangeTime);
    //{{5/1 = 5.000}, {7/1 = 7.000}}
    

    2、运算

    定义变量:

    CMTime duration = CMTimeMake(5, 1);
    CMTimeRange range = CMTimeRangeMake(duration, duration);
    CMTimeRangeShow(range);
    //{{5/1 = 5.000}, {5/1 = 5.000}}
        
    CMTime beginTime = CMTimeMake(7, 1);
    CMTime endTime = CMTimeMake(12, 1);
    CMTimeRange rangeTime = CMTimeRangeFromTimeToTime(beginTime, endTime);
    CMTimeRangeShow(rangeTime);
    //{{7/1 = 7.000}, {5/1 = 5.000}}
    

    取交叉时间范围

    CMTimeRange intersetionRange = CMTimeRangeGetIntersection(range, rangeTime);
    CMTimeRangeShow(intersetionRange);
    //{{7/1 = 7.000}, {3/1 = 3.000}}
    

    取时间范围总和

    CMTimeRange unionRange = CMTimeRangeGetUnion(range, rangeTime);
        CMTimeRangeShow(unionRange);
    //{{5/1 = 5.000}, {7/1 = 7.000}}
    

    3、转换为对象NSValue

    + (NSValue *)valueWithCMTimeRange:(CMTimeRange)timeRange

    CMTimeRange structTimeRange = CMTimeRangeMake(kCMTimeZero, kCMTimePositiveInfinity);
    
    NSValue *valueTimeRange = [NSValue valueWithCMTimeRange:structTimeRange];
    NSLog(@"%@", valueTimeRange);
    //CMTimeRange: {{0/1 = 0.000}, {+INFINITY}}
    
    structTimeRange = [valueTimeRange CMTimeRangeValue];
    CMTimeRangeShow(structTimeRange);
    //{{0/1 = 0.000}, {+INFINITY}}
    

    4、转换成字典NSDictionary

    NSDictionary *timeRangeDict = CFBridgingRelease(CMTimeRangeCopyAsDictionary(structTimeRange, NULL));
    NSLog(@"%@", timeRangeDict);
    
    structTimeRange = CMTimeRangeMakeFromDictionary((__bridge CFDictionaryRef)(timeRangeDict));
    CMTimeRangeShow(structTimeRange);
    
    /*
     {
        duration =     {
            epoch = 0;
            flags = 5;
            timescale = 0;
            value = 0;
        };
        start =     {
            epoch = 0;
            flags = 1;
            timescale = 1;
            value = 0;
        };
    }
    {{0/1 = 0.000}, {+INFINITY}}
    */
    
    

    相关文章

      网友评论

        本文标题:AVFoundation视频处理的时间CMTime

        本文链接:https://www.haomeiwen.com/subject/jyfaeftx.html