diff options
author | wm4 <wm4@nowhere> | 2014-04-23 01:17:28 +0200 |
---|---|---|
committer | wm4 <wm4@nowhere> | 2014-04-23 01:58:12 +0200 |
commit | 8a74638dc743007f6d5d6bb3a672167fce353480 (patch) | |
tree | ebfe93c575a3d801cb21cd565da29e6f1d5bd41f | |
parent | c7ab0019a388ceabda38e0d7ba5eb289f30e24af (diff) | |
download | mpv-8a74638dc743007f6d5d6bb3a672167fce353480.tar.bz2 mpv-8a74638dc743007f6d5d6bb3a672167fce353480.tar.xz |
video: add a "hwdec" property to enable or disable hw decoding at runtime
-rw-r--r-- | DOCS/man/en/input.rst | 10 | ||||
-rw-r--r-- | player/command.c | 33 | ||||
-rw-r--r-- | video/decode/lavc.h | 1 | ||||
-rw-r--r-- | video/decode/vd.h | 1 | ||||
-rw-r--r-- | video/decode/vd_lavc.c | 9 |
5 files changed, 54 insertions, 0 deletions
diff --git a/DOCS/man/en/input.rst b/DOCS/man/en/input.rst index dadf8a1901..8c5a021329 100644 --- a/DOCS/man/en/input.rst +++ b/DOCS/man/en/input.rst @@ -879,6 +879,16 @@ Property list ``hue`` (RW) See ``--hue``. +``hwdec`` (RW) + Return the current hardware decoder that is used. This uses the same values + as the ``--hwdec`` option. If software decoding is active, this returns + ``no``. You can write this property. Then the ``--hwdec`` option is set to + the new value, and video decoding will be reinitialized (internally, the + player will perform a seek to refresh the video properly). + + Note that you don't know the success of the operation immediately after + writing this property. It happens with a delay as video is reinitialized. + ``panscan`` (RW) See ``--panscan``. diff --git a/player/command.c b/player/command.c index 0cc1edde81..fd08c667c8 100644 --- a/player/command.c +++ b/player/command.c @@ -1473,6 +1473,38 @@ static int mp_property_program(m_option_t *prop, int action, void *arg, return M_PROPERTY_NOT_IMPLEMENTED; } +static int mp_property_hwdec(m_option_t *prop, int action, void *arg, + MPContext *mpctx) +{ + struct MPOpts *opts = mpctx->opts; + struct dec_video *vd = mpctx->d_video; + if (!vd) + return M_PROPERTY_UNAVAILABLE; + + int current = 0; + video_vd_control(vd, VDCTRL_GET_HWDEC, ¤t); + + switch (action) { + case M_PROPERTY_GET: + *(int *)arg = current; + return M_PROPERTY_OK; + case M_PROPERTY_SET: { + int new = *(int *)arg; + if (current == new) + return M_PROPERTY_OK; + if (!(mpctx->initialized_flags & INITIALIZED_VCODEC)) + return M_PROPERTY_ERROR; + double last_pts = mpctx->last_vo_pts; + uninit_player(mpctx, INITIALIZED_VCODEC); + opts->hwdec_api = new; + reinit_video_chain(mpctx); + if (last_pts != MP_NOPTS_VALUE) + queue_seek(mpctx, MPSEEK_ABSOLUTE, last_pts, 1, true); + return M_PROPERTY_OK; + } + } + return mp_property_generic_option(prop, action, arg, mpctx); +} /// Fullscreen state (RW) static int mp_property_fullscreen(m_option_t *prop, @@ -2348,6 +2380,7 @@ static const m_option_t mp_properties[] = { M_OPTION_PROPERTY_CUSTOM("vid", mp_property_video), { "program", mp_property_program, CONF_TYPE_INT, CONF_RANGE, -1, 65535, NULL }, + M_OPTION_PROPERTY_CUSTOM("hwdec", mp_property_hwdec), { "osd-width", mp_property_osd_w, CONF_TYPE_INT }, { "osd-height", mp_property_osd_h, CONF_TYPE_INT }, diff --git a/video/decode/lavc.h b/video/decode/lavc.h index 16d3251725..d67292c4fd 100644 --- a/video/decode/lavc.h +++ b/video/decode/lavc.h @@ -26,6 +26,7 @@ typedef struct lavc_ctx { AVCodecContext *avctx; AVFrame *pic; struct vd_lavc_hwdec *hwdec; + int selected_hwdec; enum AVPixelFormat pix_fmt; int best_csp; enum AVDiscard skip_frame; diff --git a/video/decode/vd.h b/video/decode/vd.h index 35c2739aa8..28ace3cc04 100644 --- a/video/decode/vd.h +++ b/video/decode/vd.h @@ -45,6 +45,7 @@ enum vd_ctrl { VDCTRL_RESET = 1, // reset decode state after seeking VDCTRL_QUERY_UNSEEN_FRAMES, // current decoder lag VDCTRL_FORCE_HWDEC_FALLBACK, // force software decoding fallback + VDCTRL_GET_HWDEC, }; #endif /* MPLAYER_VD_H */ diff --git a/video/decode/vd_lavc.c b/video/decode/vd_lavc.c index 4935913d73..57b391a6a2 100644 --- a/video/decode/vd_lavc.c +++ b/video/decode/vd_lavc.c @@ -225,6 +225,8 @@ static int init(struct dec_video *vd, const char *decoder) ctx->log = vd->log; ctx->opts = vd->opts; + ctx->selected_hwdec = vd->opts->hwdec_api; + if (bstr_endswith0(bstr0(decoder), "_vdpau")) { MP_WARN(vd, "VDPAU decoder '%s' was requested. " "This way of enabling hardware\ndecoding is not supported " @@ -646,6 +648,13 @@ static int control(struct dec_video *vd, int cmd, void *arg) delay += avctx->thread_count - 1; *(int *)arg = delay; return CONTROL_TRUE; + case VDCTRL_GET_HWDEC: { + int hwdec = ctx->selected_hwdec; + if (!ctx->software_fallback_decoder) + hwdec = 0; + *(int *)arg = hwdec; + return CONTROL_TRUE; + } case VDCTRL_FORCE_HWDEC_FALLBACK: return force_fallback(vd); } |