Use aspect from encoder for AVI vprp header

git-svn-id: svn://svn.mplayerhq.hu/mplayer/trunk@12062 b3059339-0415-0410-9bf9-f77b7e298cf2
This commit is contained in:
ranma 2004-03-24 15:16:36 +00:00
parent 2a3030f5f4
commit 7068c1b886
16 changed files with 63 additions and 58 deletions

View File

@ -364,27 +364,6 @@ will not be displayed.
Particularly useful on slow terminals or broken ones that do not properly
handle carriage return (i.e. \\r).
.TP
.B \-useaviaspect
With this option MPlayer and MEncoder will read and write the aspect
setting from the OpenDML AVI Video Property Header.
This is a different method than the "aspect=..." option of
libavcodec or XviD, and is prioritized over it during playback,
because this header is processed first.
Generally, encoding AVIs with square pixels is still the best
choice, so aspect headers should be avoided.
Some players can understand it, while they may not understand the
aspect headers produced by the codec.
.I EXAMPLE:
.PD 0
.RSs
.IPs "\-aspect 16:9 \-useaviaspect"
will add a header specifying 16:9 aspect ratio.
.RE
.PD 1
.TP
.B \-v, \-verbose
Increment verbose level (more \-v means more verbosity).
.
@ -3795,6 +3774,10 @@ will have the output file contain 'div3' as video fourcc.
.PD 1
.
.TP
.B \-force-avi-aspect <0.2\-3.0>
Override the aspect stored in the AVI OpenDML vprp header.
This can be used to change the aspect ratio with \-ovc copy.
.TP
.B \-info <option1:option2:...> (AVI only)
Specify the info header of the resulting AVI file.
.br

View File

@ -119,9 +119,6 @@
{"dvbin", dvbin_opts_conf, CONF_TYPE_SUBCONFIG, 0, 0, 0, NULL},
#endif
{"useaviaspect", &avi_use_vprp_aspect, CONF_TYPE_FLAG, 0, 0, 1, NULL},
{"nouseaviaspect", &avi_use_vprp_aspect, CONF_TYPE_FLAG, 0, 1, 0, NULL},
// ------------------------- a-v sync options --------------------
// AVI specific: A-V sync mode (bps vs. interleaving)
@ -319,8 +316,6 @@ extern int ts_prog;
extern int ts_keep_broken;
extern off_t ts_probe;
extern int avi_use_vprp_aspect; /* defined in aviheader.c */
#include "libmpdemux/tv.h"
#ifdef USE_EDL

View File

@ -160,6 +160,8 @@ m_option_t of_conf[]={
{NULL, NULL, 0, 0, 0, 0, NULL}
};
extern float avi_aspect_override; /* defined in libmpdemux/muxer_avi.c */
m_option_t mencoder_opts[]={
/* name, pointer, type, flags, min, max */
@ -192,6 +194,9 @@ m_option_t mencoder_opts[]={
// override FOURCC in output file
{"ffourcc", &force_fourcc, CONF_TYPE_STRING, 0, 4, 4, NULL},
// override avi aspect autodetection
{"force-avi-aspect", &avi_aspect_override, CONF_TYPE_FLOAT, CONF_RANGE, 0.2, 3.0, NULL},
{"pass", "The -pass option is obsolete. Use -lavcopts vpass=n or -divx4opts pass=n!\nRTFM!\n", CONF_TYPE_PRINT, CONF_NOCFG, 0, 0, NULL},
{"passlogfile", &passtmpfile, CONF_TYPE_STRING, 0, 0, 0, NULL},

View File

@ -211,6 +211,7 @@ static int config(struct vf_instance_s* vf,
mux_v->bih->biWidth=width;
mux_v->bih->biHeight=height;
mux_v->bih->biSizeImage=width*height*3;
mux_v->aspect = (float)d_width/d_height;
if(!divx4_param.bitrate) divx4_param.bitrate=800000;
else if(divx4_param.bitrate<=16000) divx4_param.bitrate*=1000;

View File

@ -519,6 +519,7 @@ static int config(struct vf_instance_s* vf,
#else
lavc_venc_context->aspect_ratio= ratio;
#endif
mux_v->aspect = ratio;
mp_dbg(MSGT_MENCODER, MSGL_DBG2, "aspect_ratio: %f\n", ratio);
} else {
mp_dbg(MSGT_MENCODER, MSGL_ERR, "aspect ratio: cannot parse \"%s\"\n", lavc_param_aspect);
@ -529,8 +530,9 @@ static int config(struct vf_instance_s* vf,
#if LIBAVCODEC_BUILD >= 4687
lavc_venc_context->sample_aspect_ratio = av_d2q((float)d_width/d_height*height / width, 255);
#else
lavc_venc_context->aspect_ratio = (float)d_width/d_height;
lavc_venc_context->aspect_ratio =
#endif
mux_v->aspect = (float)d_width/d_height;
/* keyframe interval */
if (lavc_param_keyint >= 0) /* != -1 */

View File

@ -55,6 +55,7 @@ static int config(struct vf_instance_s* vf,
mux_v->bih->biWidth=width;
mux_v->bih->biHeight=height;
mux_v->bih->biSizeImage=mux_v->bih->biWidth*mux_v->bih->biHeight*(mux_v->bih->biBitCount/8);
mux_v->aspect = (float)d_width/d_height;
return 1;
}

View File

@ -80,6 +80,7 @@ static int config(struct vf_instance_s* vf,
mux_v->bih->biWidth=width;
mux_v->bih->biHeight=height;
mux_v->bih->biSizeImage=mux_v->bih->biWidth*mux_v->bih->biHeight*(mux_v->bih->biBitCount/8);
mux_v->aspect = (float)d_width/d_height;
vf->priv->buffer = realloc(vf->priv->buffer,vf->priv->buf_size);
vf->priv->tbl_wrote = 0;

View File

@ -129,6 +129,7 @@ static int config(struct vf_instance_s* vf,
mux_v->bih->biWidth=width;
mux_v->bih->biHeight=height;
mux_v->bih->biSizeImage=width*height*2;
mux_v->aspect = (float)d_width/d_height;

View File

@ -83,6 +83,7 @@ static int config(struct vf_instance_s *vf,
int ret;
mux_v->bih->biWidth = width;
mux_v->bih->biHeight = height;
mux_v->aspect = (float)d_width/d_height;
ret = set_format(vf, outfmt);
if (!ret) return 0;

View File

@ -217,6 +217,7 @@ static int config(struct vf_instance_s* vf,
vfw_bih->biWidth=width;
vfw_bih->biHeight=height;
vfw_bih->biSizeImage=width*height*((vfw_bih->biBitCount+7)/8);
mux_v->aspect = (float)d_width/d_height;
if(!vfw_start_encoder(vfw_bih, mux_v->bih)) return 0;

View File

@ -172,6 +172,7 @@ config(struct vf_instance_s* vf,
fp->mux->bih->biWidth = width;
fp->mux->bih->biHeight = height;
fp->mux->bih->biSizeImage = fp->mux->bih->biWidth * fp->mux->bih->biHeight * 3;
fp->mux->aspect = (float)d_width/d_height;
mp_msg(MSGT_MENCODER,MSGL_INFO,"videocodec: XViD (%dx%d fourcc=%x [%.4s])\n",
width, height, fp->mux->bih->biCompression, (char *)&fp->mux->bih->biCompression);

View File

@ -339,6 +339,7 @@ config(struct vf_instance_s* vf,
mod->mux->bih->biHeight = height;
mod->mux->bih->biSizeImage =
mod->mux->bih->biWidth * mod->mux->bih->biHeight * 3;
mod->mux->aspect = (float)d_width/d_height;
/* Message the FourCC type */
mp_msg(MSGT_MENCODER, MSGL_INFO,

View File

@ -28,8 +28,6 @@ extern void print_index(AVIINDEXENTRY *idx,int idx_size);
extern void print_avistdindex_chunk(avistdindex_chunk *h);
extern void print_avisuperindex_chunk(avisuperindex_chunk *h);
int avi_use_vprp_aspect = 0;
static int odml_get_vstream_id(int id, unsigned char res[])
{
unsigned char *p = (unsigned char *)&id;
@ -345,7 +343,7 @@ while(1){
for (i=0; i<vprp->nbFieldPerFrame; i++) {
le2me_VIDEO_FIELD_DESC(&vprp->FieldInfo[i]);
}
if (avi_use_vprp_aspect && sh_video) {
if (sh_video) {
sh_video->aspect = GET_AVI_ASPECT(vprp->dwFrameAspectRatio);
}
if(verbose>=1) print_vprp(vprp);

View File

@ -17,6 +17,7 @@ typedef struct {
uint32_t ckid; // chunk id (00dc 01wb etc)
double timer;
off_t size;
float aspect; // aspect ratio of this stream (set by ve_*.c)
// buffering:
unsigned char *buffer;
unsigned int buffer_size;

View File

@ -34,7 +34,7 @@ extern char *info_comment;
#define ODML_NOTKEYFRAME 0x80000000U
#define MOVIALIGN 0x00001000
extern int avi_use_vprp_aspect;
float avi_aspect_override = -1.0;
struct avi_odmlidx_entry {
uint64_t ofs;
@ -57,6 +57,35 @@ struct avi_stream_info {
struct avi_odmlsuperidx_entry *superidx;
};
static unsigned int avi_aspect(muxer_stream_t *vstream)
{
int x,y;
float aspect = vstream->aspect;
if (avi_aspect_override > 0.0) {
aspect = avi_aspect_override;
}
if (aspect <= 0.0) return 0;
if (aspect > 15.99/9.0 && aspect < 16.01/9.0) {
return MAKE_AVI_ASPECT(16, 9);
}
if (aspect > 3.99/3.0 && aspect < 4.01/3.0) {
return MAKE_AVI_ASPECT(4, 3);
}
if (aspect >= 1.0) {
x = 16384;
y = (float)x / aspect;
} else {
y = 16384;
x = (float)y * aspect;
}
return MAKE_AVI_ASPECT(x, y);
}
static muxer_stream_t* avifile_new_stream(muxer_t *muxer,int type){
struct avi_stream_info *si;
muxer_stream_t* s;
@ -225,21 +254,6 @@ static void write_avi_list(FILE *f,unsigned int id,int len){
#define WFSIZE(wf) (sizeof(WAVEFORMATEX)+(wf)->cbSize)
static unsigned int avi_aspect(float aspect)
{
if (aspect <= 0.0) {
aspect = 4.0/3.0;
}
if (aspect >= 3.99/3.0 &&
aspect <= 4.01/3.0) return MAKE_AVI_ASPECT(4,3);
if (aspect >= 15.99/9.0 &&
aspect <= 16.01/9.0) return MAKE_AVI_ASPECT(16,9);
if (aspect >= 0.99 &&
aspect <= 1.01) return MAKE_AVI_ASPECT(1,1);
if (aspect<1.0) return MAKE_AVI_ASPECT((int)(aspect*8192),8192);
return MAKE_AVI_ASPECT(8192,(int)(8192/aspect));
}
static void avifile_write_header(muxer_t *muxer){
uint32_t riff[3];
unsigned int dmlh[1];
@ -248,10 +262,16 @@ static void avifile_write_header(muxer_t *muxer){
muxer_info_t info[16];
FILE *f = muxer->file;
VideoPropHeader vprp;
uint32_t aspect = avi_aspect(muxer->def_v);
off_t pos;
int isodml = muxer->file_end > ODML_CHUNKLEN ? 1 : 0;
if (aspect == 0) {
mp_msg(MSGT_MUXER, MSGL_INFO, "ODML: Aspect information not (yet?) available or unspecified, not writing vprp header.\n");
} else {
mp_msg(MSGT_MUXER, MSGL_INFO, "ODML: vprp aspect is %d:%d.\n", aspect >> 16, aspect & 0xffff);
}
if (isodml) {
for (pos = 0; pos < muxer->file_end; pos += ODML_CHUNKLEN) {
unsigned int rifflen, movilen;
@ -316,7 +336,7 @@ static void avifile_write_header(muxer_t *muxer){
switch(muxer->streams[i]->type){
case MUXER_TYPE_VIDEO:
hdrsize+=muxer->streams[i]->bih->biSize+8; // strf
if (avi_use_vprp_aspect) {
if (aspect != 0) {
hdrsize+=8+4*(9+8*1); // vprp
}
break;
@ -351,14 +371,13 @@ static void avifile_write_header(muxer_t *muxer){
s->h.fccHandler = s->bih->biCompression;
s->h.rcFrame.right = s->bih->biWidth;
s->h.rcFrame.bottom = s->bih->biHeight;
if (avi_use_vprp_aspect) {
sh_video_t *sh_video = s->source;
if (aspect != 0) {
// fill out vprp info
memset(&vprp, 0, sizeof(vprp));
vprp.dwVerticalRefreshRate = (s->h.dwRate+s->h.dwScale-1)/s->h.dwScale;
vprp.dwHTotalInT = muxer->avih.dwWidth;
vprp.dwVTotalInLines = muxer->avih.dwHeight;
vprp.dwFrameAspectRatio = avi_aspect(sh_video->aspect);
vprp.dwFrameAspectRatio = aspect;
vprp.dwFrameWidthInPixels = muxer->avih.dwWidth;
vprp.dwFrameHeightInLines = muxer->avih.dwHeight;
vprp.nbFieldPerFrame = 1;
@ -388,7 +407,7 @@ static void avifile_write_header(muxer_t *muxer){
write_avi_chunk(f,ckidSTREAMFORMAT,biSize,s->bih); /* BITMAPINFOHEADER */
le2me_BITMAPINFOHEADER(s->bih);
if (avi_use_vprp_aspect) {
if (aspect != 0) {
int fields = vprp.nbFieldPerFrame;
le2me_VideoPropHeader(&vprp);
le2me_VIDEO_FIELD_DESC(&vprp.FieldInfo[0]);

View File

@ -663,12 +663,6 @@ case VCODEC_COPY:
mux_v->bih->biBitCount=24; // FIXME!!!
mux_v->bih->biSizeImage=mux_v->bih->biWidth*mux_v->bih->biHeight*(mux_v->bih->biBitCount/8);
}
/*
* FIXME: with -ovc copy we don't get aspect ratio information
* from the source stream.
*/
if(movie_aspect>-1.0) sh_video->aspect = movie_aspect;
printf("videocodec: framecopy (%dx%d %dbpp fourcc=%x)\n",
mux_v->bih->biWidth, mux_v->bih->biHeight,
mux_v->bih->biBitCount, mux_v->bih->biCompression);