diff options
author | Uoti Urpala <uau@glyph.nonexistent.invalid> | 2010-01-25 15:59:53 +0200 |
---|---|---|
committer | Uoti Urpala <uau@glyph.nonexistent.invalid> | 2010-01-25 15:59:53 +0200 |
commit | e28e4a1b157bd0e9620fcff956d713a9921f506c (patch) | |
tree | d92e54e1e25feb84e692396cf234478f403e5738 /libmpcodecs | |
parent | 560acfd0407c757e17bf72b490687d4947b05675 (diff) | |
parent | 213092c8dcfc925d8d54cf320b60cf298a870696 (diff) | |
download | mpv-e28e4a1b157bd0e9620fcff956d713a9921f506c.tar.bz2 mpv-e28e4a1b157bd0e9620fcff956d713a9921f506c.tar.xz |
Merge svn changes up to r30419
Diffstat (limited to 'libmpcodecs')
-rw-r--r-- | libmpcodecs/vd.c | 13 | ||||
-rw-r--r-- | libmpcodecs/vf_fspp.c | 12 | ||||
-rw-r--r-- | libmpcodecs/vf_halfpack.c | 24 | ||||
-rw-r--r-- | libmpcodecs/vf_scale.c | 51 | ||||
-rw-r--r-- | libmpcodecs/vf_spp.c | 10 |
5 files changed, 88 insertions, 22 deletions
diff --git a/libmpcodecs/vd.c b/libmpcodecs/vd.c index 1910af62ee..1821498865 100644 --- a/libmpcodecs/vd.c +++ b/libmpcodecs/vd.c @@ -189,7 +189,7 @@ int mpcodecs_config_vo(sh_video_t *sh, int w, int h, } else { // sws failed, if the last filter (vf_vo) support MPEGPES try // to append vf_lavc - vf_instance_t *vo, *vp = NULL, *ve; + vf_instance_t *vo, *vp = NULL, *ve, *vpp = NULL; // Remove the scale filter if we added it ourselves if (vf == sc) { ve = vf; @@ -197,8 +197,10 @@ int mpcodecs_config_vo(sh_video_t *sh, int w, int h, vf_uninit_filter(ve); } // Find the last filter (vf_vo) - for (vo = vf; vo->next; vo = vo->next) + for (vo = vf; vo->next; vo = vo->next) { + vpp = vp; vp = vo; + } if (vo->query_format(vo, IMGFMT_MPEGPES) && (!vp || (vp && strcmp(vp->info->name, "lavc")))) { ve = vf_open_filter(opts, vo, "lavc", NULL); @@ -208,6 +210,13 @@ int mpcodecs_config_vo(sh_video_t *sh, int w, int h, vf = ve; goto csp_again; } + if (vp && !strcmp(vp->info->name,"lavc")) { + if (vpp) + vpp->next = vo; + else + vf = vo; + vf_uninit_filter(vp); + } } mp_tmsg(MSGT_CPLAYER, MSGL_WARN, "The selected video_out device is incompatible with this codec.\n"\ diff --git a/libmpcodecs/vf_fspp.c b/libmpcodecs/vf_fspp.c index 7264199c21..8ef33381b1 100644 --- a/libmpcodecs/vf_fspp.c +++ b/libmpcodecs/vf_fspp.c @@ -533,9 +533,15 @@ static int put_image(struct vf_instance* vf, mp_image_t *mpi, double pts) vf->priv->mpeg2= mpi->qscale_type; if(mpi->pict_type != 3 && mpi->qscale && !vf->priv->qp){ - if(!vf->priv->non_b_qp) - vf->priv->non_b_qp= malloc(mpi->qstride * ((mpi->h + 15) >> 4)); - fast_memcpy(vf->priv->non_b_qp, mpi->qscale, mpi->qstride * ((mpi->h + 15) >> 4)); + int w = mpi->qstride; + int h = (mpi->h + 15) >> 4; + if (!w) { + w = (mpi->w + 15) >> 4; + h = 1; + } + if(!vf->priv->non_b_qp) + vf->priv->non_b_qp= malloc(w*h); + fast_memcpy(vf->priv->non_b_qp, mpi->qscale, w*h); } if(vf->priv->log2_count || !(mpi->flags&MP_IMGFLAG_DIRECT)){ char *qp_tab= vf->priv->non_b_qp; diff --git a/libmpcodecs/vf_halfpack.c b/libmpcodecs/vf_halfpack.c index 682b80a91e..4a3bdb578f 100644 --- a/libmpcodecs/vf_halfpack.c +++ b/libmpcodecs/vf_halfpack.c @@ -10,11 +10,14 @@ #include "img_format.h" #include "mp_image.h" #include "vf.h" +#include "vf_scale.h" -#include "libswscale/rgb2rgb.h" +#include "libswscale/swscale.h" +#include "fmt-conversion.h" struct vf_priv_s { int field; + struct SwsContext *ctx; }; #if HAVE_MMX @@ -144,6 +147,10 @@ static void (*halfpack)(unsigned char *dst, unsigned char *src[3], static int put_image(struct vf_instance* vf, mp_image_t *mpi, double pts) { + const uint8_t *src[MP_MAX_PLANES] = { + mpi->planes[0] + mpi->stride[0]*vf->priv->field, + mpi->planes[1], mpi->planes[2], NULL}; + int src_stride[MP_MAX_PLANES] = {mpi->stride[0]*2, mpi->stride[1], mpi->stride[2], 0}; mp_image_t *dmpi; // hope we'll get DR buffer: @@ -154,9 +161,8 @@ static int put_image(struct vf_instance* vf, mp_image_t *mpi, double pts) switch(vf->priv->field) { case 0: case 1: - yuv422ptoyuy2(mpi->planes[0] + mpi->stride[0]*vf->priv->field, - mpi->planes[1], mpi->planes[2], dmpi->planes[0], - mpi->w, mpi->h/2, mpi->stride[0]*2, mpi->stride[1], dmpi->stride[0]); + sws_scale(vf->priv->ctx, src, src_stride, + 0, mpi->h/2, dmpi->planes, dmpi->stride); break; default: halfpack(dmpi->planes[0], mpi->planes, dmpi->stride[0], @@ -170,6 +176,15 @@ static int config(struct vf_instance* vf, int width, int height, int d_width, int d_height, unsigned int flags, unsigned int outfmt) { + if (vf->priv->field < 2) { + sws_freeContext(vf->priv->ctx); + // get unscaled 422p -> yuy2 conversion + vf->priv->ctx = + sws_getContext(width, height / 2, PIX_FMT_YUV422P, + width, height / 2, PIX_FMT_YUYV422, + SWS_POINT | SWS_PRINT_INFO | get_sws_cpuflags(), + NULL, NULL, NULL); + } /* FIXME - also support UYVY output? */ return vf_next_config(vf, width, height/2, d_width, d_height, flags, IMGFMT_YUY2); } @@ -189,6 +204,7 @@ static int query_format(struct vf_instance* vf, unsigned int fmt) static void uninit(struct vf_instance* vf) { + sws_freeContext(vf->priv->ctx); free(vf->priv); } diff --git a/libmpcodecs/vf_scale.c b/libmpcodecs/vf_scale.c index a38cf895d9..82a56535bb 100644 --- a/libmpcodecs/vf_scale.c +++ b/libmpcodecs/vf_scale.c @@ -31,7 +31,6 @@ static struct vf_priv_s { int interlaced; int noup; int accurate_rnd; - int query_format_cache[64]; } const vf_priv_dflt = { -1,-1, 0, @@ -92,18 +91,48 @@ static const unsigned int outfmt_list[]={ 0 }; -static unsigned int find_best_out(vf_instance_t *vf){ +/** + * A list of preferred conversions, in order of preference. + * This should be used for conversions that e.g. involve no scaling + * or to stop vf_scale from choosing a conversion that has no + * fast assembler implementation. + */ +static int preferred_conversions[][2] = { + {IMGFMT_YUY2, IMGFMT_UYVY}, + {IMGFMT_YUY2, IMGFMT_422P}, + {IMGFMT_UYVY, IMGFMT_YUY2}, + {IMGFMT_UYVY, IMGFMT_422P}, + {IMGFMT_422P, IMGFMT_YUY2}, + {IMGFMT_422P, IMGFMT_UYVY}, + {0, 0} +}; + +static unsigned int find_best_out(vf_instance_t *vf, int in_format){ unsigned int best=0; - int i; + int i = -1; + int j = -1; + int format = 0; // find the best outfmt: - for(i=0; i<sizeof(outfmt_list)/sizeof(int)-1; i++){ - const int format= outfmt_list[i]; - int ret= vf->priv->query_format_cache[i]-1; - if(ret == -1){ - ret= vf_next_query_format(vf, outfmt_list[i]); - vf->priv->query_format_cache[i]= ret+1; + while (1) { + int ret; + if (j < 0) { + format = in_format; + j = 0; + } else if (i < 0) { + while (preferred_conversions[j][0] && + preferred_conversions[j][0] != in_format) + j++; + format = preferred_conversions[j++][1]; + // switch to standard list + if (!format) + i = 0; } + if (i >= 0) + format = outfmt_list[i++]; + if (!format) + break; + ret = vf_next_query_format(vf, format); mp_msg(MSGT_VFILTER,MSGL_DBG2,"scale: query(%s) -> %d\n",vo_format_name(format),ret&3); if(ret&VFCAP_CSP_SUPPORTED_BY_HW){ @@ -120,7 +149,7 @@ static int config(struct vf_instance* vf, int width, int height, int d_width, int d_height, unsigned int flags, unsigned int outfmt){ struct MPOpts *opts = vf->opts; - unsigned int best=find_best_out(vf); + unsigned int best=find_best_out(vf, outfmt); int vo_flags; int int_sws_flags=0; int round_w=0, round_h=0; @@ -494,7 +523,7 @@ static int query_format(struct vf_instance* vf, unsigned int fmt){ case IMGFMT_RGB48LE: case IMGFMT_RGB48BE: { - unsigned int best=find_best_out(vf); + unsigned int best=find_best_out(vf, fmt); int flags; if(!best) return 0; // no matching out-fmt flags=vf_next_query_format(vf,best); diff --git a/libmpcodecs/vf_spp.c b/libmpcodecs/vf_spp.c index 85d7ff9fc1..8dfcf41b5c 100644 --- a/libmpcodecs/vf_spp.c +++ b/libmpcodecs/vf_spp.c @@ -475,9 +475,15 @@ static int put_image(struct vf_instance* vf, mp_image_t *mpi, double pts){ vf->priv->mpeg2= mpi->qscale_type; if(mpi->pict_type != 3 && mpi->qscale && !vf->priv->qp){ + int w = mpi->qstride; + int h = (mpi->h + 15) >> 4; + if (!w) { + w = (mpi->w + 15) >> 4; + h = 1; + } if(!vf->priv->non_b_qp) - vf->priv->non_b_qp= malloc(mpi->qstride * ((mpi->h + 15) >> 4)); - fast_memcpy(vf->priv->non_b_qp, mpi->qscale, mpi->qstride * ((mpi->h + 15) >> 4)); + vf->priv->non_b_qp= malloc(w*h); + fast_memcpy(vf->priv->non_b_qp, mpi->qscale, w*h); } if(vf->priv->log2_count || !(mpi->flags&MP_IMGFLAG_DIRECT)){ char *qp_tab= vf->priv->non_b_qp; |