Mercurial > libavcodec.hg
comparison ratecontrol.c @ 1683:043b6d933fc6 libavcodec
CBR improvements
author | michael |
---|---|
date | Fri, 12 Dec 2003 19:26:55 +0000 |
parents | 932d306bf1dc |
children | 19e781619e3f |
comparison
equal
deleted
inserted
replaced
1682:7b810155650f | 1683:043b6d933fc6 |
---|---|
1 /* | 1 /* |
2 * Rate control for video encoders | 2 * Rate control for video encoders |
3 * | 3 * |
4 * Copyright (c) 2002 Michael Niedermayer <michaelni@gmx.at> | 4 * Copyright (c) 2002-2003 Michael Niedermayer <michaelni@gmx.at> |
5 * | 5 * |
6 * This library is free software; you can redistribute it and/or | 6 * This library is free software; you can redistribute it and/or |
7 * modify it under the terms of the GNU Lesser General Public | 7 * modify it under the terms of the GNU Lesser General Public |
8 * License as published by the Free Software Foundation; either | 8 * License as published by the Free Software Foundation; either |
9 * version 2 of the License, or (at your option) any later version. | 9 * version 2 of the License, or (at your option) any later version. |
60 rcc->mv_bits_sum[i]= | 60 rcc->mv_bits_sum[i]= |
61 rcc->qscale_sum [i]= | 61 rcc->qscale_sum [i]= |
62 rcc->frame_count[i]= 1; // 1 is better cuz of 1/0 and such | 62 rcc->frame_count[i]= 1; // 1 is better cuz of 1/0 and such |
63 rcc->last_qscale_for[i]=FF_QP2LAMBDA * 5; | 63 rcc->last_qscale_for[i]=FF_QP2LAMBDA * 5; |
64 } | 64 } |
65 rcc->buffer_index= s->avctx->rc_buffer_size/2; | 65 rcc->buffer_index= s->avctx->rc_initial_buffer_occupancy; |
66 | 66 |
67 if(s->flags&CODEC_FLAG_PASS2){ | 67 if(s->flags&CODEC_FLAG_PASS2){ |
68 int i; | 68 int i; |
69 char *p; | 69 char *p; |
70 | 70 |
200 const double fps= (double)s->avctx->frame_rate / (double)s->avctx->frame_rate_base; | 200 const double fps= (double)s->avctx->frame_rate / (double)s->avctx->frame_rate_base; |
201 const double buffer_size= s->avctx->rc_buffer_size; | 201 const double buffer_size= s->avctx->rc_buffer_size; |
202 const double min_rate= s->avctx->rc_min_rate/fps; | 202 const double min_rate= s->avctx->rc_min_rate/fps; |
203 const double max_rate= s->avctx->rc_max_rate/fps; | 203 const double max_rate= s->avctx->rc_max_rate/fps; |
204 | 204 |
205 //printf("%f %f %d %f %f\n", buffer_size, rcc->buffer_index, frame_size, min_rate, max_rate); | |
205 if(buffer_size){ | 206 if(buffer_size){ |
207 int left; | |
208 | |
206 rcc->buffer_index-= frame_size; | 209 rcc->buffer_index-= frame_size; |
207 if(rcc->buffer_index < buffer_size/2 /*FIXME /2 */ || min_rate==0){ | 210 if(rcc->buffer_index < 0){ |
208 rcc->buffer_index+= max_rate; | |
209 if(rcc->buffer_index >= buffer_size) | |
210 rcc->buffer_index= buffer_size-1; | |
211 }else{ | |
212 rcc->buffer_index+= min_rate; | |
213 } | |
214 | |
215 if(rcc->buffer_index < 0) | |
216 av_log(s->avctx, AV_LOG_ERROR, "rc buffer underflow\n"); | 211 av_log(s->avctx, AV_LOG_ERROR, "rc buffer underflow\n"); |
217 if(rcc->buffer_index >= s->avctx->rc_buffer_size) | 212 rcc->buffer_index= 0; |
213 } | |
214 | |
215 left= buffer_size - rcc->buffer_index - 1; | |
216 rcc->buffer_index += clip(left, min_rate, max_rate); | |
217 | |
218 if(rcc->buffer_index > s->avctx->rc_buffer_size){ | |
218 av_log(s->avctx, AV_LOG_ERROR, "rc buffer overflow\n"); | 219 av_log(s->avctx, AV_LOG_ERROR, "rc buffer overflow\n"); |
220 rcc->buffer_index= s->avctx->rc_buffer_size; | |
221 } | |
219 } | 222 } |
220 } | 223 } |
221 | 224 |
222 /** | 225 /** |
223 * modifies the bitrate curve from pass1 for one frame | 226 * modifies the bitrate curve from pass1 for one frame |
383 RateControlContext *rcc= &s->rc_context; | 386 RateControlContext *rcc= &s->rc_context; |
384 int qmin, qmax; | 387 int qmin, qmax; |
385 double bits; | 388 double bits; |
386 const int pict_type= rce->new_pict_type; | 389 const int pict_type= rce->new_pict_type; |
387 const double buffer_size= s->avctx->rc_buffer_size; | 390 const double buffer_size= s->avctx->rc_buffer_size; |
388 const double min_rate= s->avctx->rc_min_rate; | 391 const double fps= (double)s->avctx->frame_rate / (double)s->avctx->frame_rate_base; |
389 const double max_rate= s->avctx->rc_max_rate; | 392 const double min_rate= s->avctx->rc_min_rate / fps; |
393 const double max_rate= s->avctx->rc_max_rate / fps; | |
390 | 394 |
391 get_qminmax(&qmin, &qmax, s, pict_type); | 395 get_qminmax(&qmin, &qmax, s, pict_type); |
392 | 396 |
393 /* modulation */ | 397 /* modulation */ |
394 if(s->avctx->rc_qmod_freq && frame_num%s->avctx->rc_qmod_freq==0 && pict_type==P_TYPE) | 398 if(s->avctx->rc_qmod_freq && frame_num%s->avctx->rc_qmod_freq==0 && pict_type==P_TYPE) |
404 double d= 2*(buffer_size - expected_size)/buffer_size; | 408 double d= 2*(buffer_size - expected_size)/buffer_size; |
405 if(d>1.0) d=1.0; | 409 if(d>1.0) d=1.0; |
406 else if(d<0.0001) d=0.0001; | 410 else if(d<0.0001) d=0.0001; |
407 q*= pow(d, 1.0/s->avctx->rc_buffer_aggressivity); | 411 q*= pow(d, 1.0/s->avctx->rc_buffer_aggressivity); |
408 | 412 |
409 q= FFMIN(q, bits2qp(rce, FFMAX((min_rate - buffer_size + rcc->buffer_index)*2, 1))); | 413 q= FFMIN(q, bits2qp(rce, FFMAX((min_rate - buffer_size + rcc->buffer_index)*3, 1))); |
410 } | 414 } |
411 | 415 |
412 if(max_rate){ | 416 if(max_rate){ |
413 double d= 2*expected_size/buffer_size; | 417 double d= 2*expected_size/buffer_size; |
414 if(d>1.0) d=1.0; | 418 if(d>1.0) d=1.0; |
415 else if(d<0.0001) d=0.0001; | 419 else if(d<0.0001) d=0.0001; |
416 q/= pow(d, 1.0/s->avctx->rc_buffer_aggressivity); | 420 q/= pow(d, 1.0/s->avctx->rc_buffer_aggressivity); |
417 | 421 |
418 q= FFMAX(q, bits2qp(rce, FFMAX(rcc->buffer_index/2, 1))); | 422 q= FFMAX(q, bits2qp(rce, FFMAX(rcc->buffer_index/3, 1))); |
419 } | 423 } |
420 } | 424 } |
421 //printf("q:%f max:%f min:%f size:%f index:%d bits:%f agr:%f\n", q,max_rate, min_rate, buffer_size, rcc->buffer_index, bits, s->avctx->rc_buffer_aggressivity); | 425 //printf("q:%f max:%f min:%f size:%f index:%d bits:%f agr:%f\n", q,max_rate, min_rate, buffer_size, rcc->buffer_index, bits, s->avctx->rc_buffer_aggressivity); |
422 if(s->avctx->rc_qsquish==0.0 || qmin==qmax){ | 426 if(s->avctx->rc_qsquish==0.0 || qmin==qmax){ |
423 if (q<qmin) q=qmin; | 427 if (q<qmin) q=qmin; |