summaryrefslogtreecommitdiff
path: root/libswresample/swresample.c
diff options
context:
space:
mode:
authorMichael Niedermayer <michaelni@gmx.at>2012-05-19 18:44:34 +0200
committerMichael Niedermayer <michaelni@gmx.at>2012-05-19 19:23:37 +0200
commit72a242c99832b9ef312222ac9181634f14963107 (patch)
tree8adc3da12c6b1fc9b7db909efec365111cc99582 /libswresample/swresample.c
parentf88f705abcb925cede3ffa392156489956e8c0b9 (diff)
swr: add swr_next_pts()
parameter descriptions partly reuse text from af_asyncts Signed-off-by: Michael Niedermayer <michaelni@gmx.at>
Diffstat (limited to 'libswresample/swresample.c')
-rw-r--r--libswresample/swresample.c43
1 files changed, 42 insertions, 1 deletions
diff --git a/libswresample/swresample.c b/libswresample/swresample.c
index 83bec202eb..dcc9a286c8 100644
--- a/libswresample/swresample.c
+++ b/libswresample/swresample.c
@@ -24,6 +24,8 @@
#include "libavutil/avassert.h"
#include "libavutil/audioconvert.h"
+#include <float.h>
+
#define C30DB M_SQRT2
#define C15DB 1.189207115
#define C__0DB 1.0
@@ -78,6 +80,15 @@ static const AVOption options[]={
{"phase_shift" , "Resampling Phase Shift" , OFFSET(phase_shift) , AV_OPT_TYPE_INT , {.dbl=10 }, 0 , 30 , PARAM },
{"linear_interp" , "Use Linear Interpolation" , OFFSET(linear_interp) , AV_OPT_TYPE_INT , {.dbl=0 }, 0 , 1 , PARAM },
{"cutoff" , "Cutoff Frequency Ratio" , OFFSET(cutoff) , AV_OPT_TYPE_DOUBLE,{.dbl=0.8 }, 0 , 1 , PARAM },
+{"min_comp" , "Minimum difference between timestamps and audio data (in seconds) below which no timestamp compensation of either kind is applied"
+ , OFFSET(min_compensation),AV_OPT_TYPE_FLOAT ,{.dbl=FLT_MAX }, 0 , FLT_MAX , PARAM },
+{"min_hard_comp" , "Minimum difference between timestamps and audio data (in seconds) to trigger padding/trimming the data."
+ , OFFSET(min_hard_compensation),AV_OPT_TYPE_FLOAT ,{.dbl=0.1 }, 0 , INT_MAX , PARAM },
+{"comp_duration" , "Duration (in seconds) over which data is stretched/squeezeed to make it match the timestamps."
+ , OFFSET(soft_compensation_duration),AV_OPT_TYPE_FLOAT ,{.dbl=1 }, 0 , INT_MAX , PARAM },
+{"max_soft_comp" , "Maximum factor by which data is stretched/squeezeed to make it match the timestamps."
+ , OFFSET(max_soft_compensation),AV_OPT_TYPE_FLOAT ,{.dbl=0 }, 0 , INT_MAX , PARAM },
+
{0}
};
@@ -644,7 +655,10 @@ int swr_convert(struct SwrContext *s, uint8_t *out_arg[SWR_CH_MAX], int out_coun
fill_audiodata(out, out_arg);
if(s->resample){
- return swr_convert_internal(s, out, out_count, in, in_count);
+ int ret = swr_convert_internal(s, out, out_count, in, in_count);
+ if(ret>0 && !s->drop_output)
+ s->outpts += ret * (int64_t)s->in_sample_rate;
+ return ret;
}else{
AudioData tmp= *in;
int ret2=0;
@@ -693,6 +707,8 @@ int swr_convert(struct SwrContext *s, uint8_t *out_arg[SWR_CH_MAX], int out_coun
s->in_buffer_count += in_count;
}
}
+ if(ret2>0 && !s->drop_output)
+ s->outpts += ret2 * (int64_t)s->in_sample_rate;
return ret2;
}
}
@@ -731,3 +747,28 @@ int swr_inject_silence(struct SwrContext *s, int count){
av_freep(&silence.data);
return ret;
}
+
+int64_t swr_next_pts(struct SwrContext *s, int64_t pts){
+ if(pts == INT64_MIN)
+ return s->outpts;
+ if(s->min_compensation >= FLT_MAX) {
+ return (s->outpts = pts - swr_get_delay(s, s->in_sample_rate * (int64_t)s->out_sample_rate));
+ } else {
+ int64_t delta = pts - swr_get_delay(s, s->in_sample_rate * (int64_t)s->out_sample_rate) - s->outpts;
+ double fdelta = delta /(double)(s->in_sample_rate * (int64_t)s->out_sample_rate);
+
+ if(fabs(fdelta) > s->min_compensation) {
+ if(!s->outpts || fabs(fdelta) > s->min_hard_compensation){
+ if(delta > 0) swr_inject_silence(s, delta / s->out_sample_rate);
+ else swr_drop_output (s, -delta / s-> in_sample_rate);
+ } else {
+ int duration = s->out_sample_rate * s->soft_compensation_duration;
+ int comp = av_clipf(fdelta, -s->max_soft_compensation, s->max_soft_compensation) * duration ;
+ av_log(s, AV_LOG_VERBOSE, "compensating audio timestamp drift:%f compensation:%d in:%d\n", fdelta, comp, duration);
+ swr_set_compensation(s, comp, duration);
+ }
+ }
+
+ return s->outpts;
+ }
+}