diff options
Diffstat (limited to 'command.c')
-rw-r--r-- | command.c | 140 |
1 files changed, 107 insertions, 33 deletions
@@ -41,6 +41,7 @@ #include "libmpcodecs/vd.h" #include "mp_osd.h" #include "libvo/video_out.h" +#include "libvo/csputils.h" #include "sub/font_load.h" #include "playtree.h" #include "libao2/audio_out.h" @@ -1152,48 +1153,114 @@ static int mp_property_deinterlace(m_option_t *prop, int action, return m_property_flag_ro(prop, action, arg, value); } -static int mp_property_yuv_colorspace(m_option_t *prop, int action, +static int colormatrix_property_helper(m_option_t *prop, int action, void *arg, MPContext *mpctx) { - if (!mpctx->sh_video || !mpctx->sh_video->vfilter) - return M_PROPERTY_UNAVAILABLE; + int r = mp_property_generic_option(prop, action, arg, mpctx); + // testing for an actual change is too much effort + switch (action) { + case M_PROPERTY_SET: + case M_PROPERTY_STEP_UP: + case M_PROPERTY_STEP_DOWN: + if (mpctx->sh_video) + set_video_colorspace(mpctx->sh_video); + break; + } + return r; +} - struct vf_instance *vf = mpctx->sh_video->vfilter; - int colorspace; +static int mp_property_colormatrix(m_option_t *prop, int action, void *arg, + MPContext *mpctx) +{ + struct MPOpts *opts = &mpctx->opts; switch (action) { - case M_PROPERTY_GET: - if (!arg) - return M_PROPERTY_ERROR; - if (vf->control(vf, VFCTRL_GET_YUV_COLORSPACE, arg) != true) - return M_PROPERTY_UNAVAILABLE; - return M_PROPERTY_OK; case M_PROPERTY_PRINT: if (!arg) return M_PROPERTY_ERROR; - if (vf->control(vf, VFCTRL_GET_YUV_COLORSPACE, &colorspace) != true) - return M_PROPERTY_UNAVAILABLE; - char *const names[] = { - "BT.601 (SD)", "BT.709 (HD)", "SMPTE-240M" - }; - if (colorspace < 0 || colorspace >= sizeof(names) / sizeof(names[0])) - *(char **)arg = talloc_strdup(NULL, mp_gtext("unknown")); - else - *(char **)arg = talloc_strdup(NULL, names[colorspace]); + struct mp_csp_details actual = { .format = -1 }; + char *req_csp = mp_csp_names[opts->requested_colorspace]; + char *real_csp = NULL; + if (mpctx->sh_video) { + struct vf_instance *vf = mpctx->sh_video->vfilter; + if (vf->control(vf, VFCTRL_GET_YUV_COLORSPACE, &actual) == true) { + real_csp = mp_csp_names[actual.format]; + } else { + real_csp = "Unknown"; + } + } + char *res; + if (opts->requested_colorspace == MP_CSP_AUTO && real_csp) { + // Caveat: doesn't handle the case when the autodetected colorspace + // is different from the actual colorspace as used by the + // VO - the OSD will display the VO colorspace without + // indication that it doesn't match the requested colorspace. + res = talloc_asprintf(NULL, "Auto (%s)", real_csp); + } else if (opts->requested_colorspace == actual.format || !real_csp) { + res = talloc_strdup(NULL, req_csp); + } else + res = talloc_asprintf(NULL, mp_gtext("%s, but %s used"), + req_csp, real_csp); + *(char **)arg = res; return M_PROPERTY_OK; - case M_PROPERTY_SET: + default:; + return colormatrix_property_helper(prop, action, arg, mpctx); + } +} + +static int levels_property_helper(int offset, m_option_t *prop, int action, + void *arg, MPContext *mpctx) +{ + char *optname = prop->priv; + const struct m_option *opt = m_config_get_option(mpctx->mconfig, + bstr(optname)); + int *valptr = (int *)m_option_get_ptr(opt, &mpctx->opts); + + switch (action) { + case M_PROPERTY_PRINT: if (!arg) return M_PROPERTY_ERROR; - M_PROPERTY_CLAMP(prop, *(int *) arg); - vf->control(vf, VFCTRL_SET_YUV_COLORSPACE, arg); - return M_PROPERTY_OK; - case M_PROPERTY_STEP_UP:; - if (vf->control(vf, VFCTRL_GET_YUV_COLORSPACE, &colorspace) != true) - return M_PROPERTY_UNAVAILABLE; - colorspace += 1; - vf->control(vf, VFCTRL_SET_YUV_COLORSPACE, &colorspace); + struct mp_csp_details actual = {0}; + int actual_level = -1; + char *req_level = m_option_print(opt, valptr); + char *real_level = NULL; + if (mpctx->sh_video) { + struct vf_instance *vf = mpctx->sh_video->vfilter; + if (vf->control(vf, VFCTRL_GET_YUV_COLORSPACE, &actual) == true) { + actual_level = *(enum mp_csp_levels *)(((char *)&actual) + offset); + real_level = m_option_print(opt, &actual_level); + } else { + real_level = talloc_strdup(NULL, "Unknown"); + } + } + char *res; + if (*valptr == MP_CSP_LEVELS_AUTO && real_level) { + res = talloc_asprintf(NULL, "Auto (%s)", real_level); + } else if (*valptr == actual_level || !real_level) { + res = talloc_strdup(NULL, real_level); + } else + res = talloc_asprintf(NULL, mp_gtext("%s, but %s used"), + req_level, real_level); + talloc_free(req_level); + talloc_free(real_level); + *(char **)arg = res; return M_PROPERTY_OK; + default:; + return colormatrix_property_helper(prop, action, arg, mpctx); } - return M_PROPERTY_NOT_IMPLEMENTED; +} + +static int mp_property_colormatrix_input_range(m_option_t *prop, int action, + void *arg, MPContext *mpctx) +{ + return levels_property_helper(offsetof(struct mp_csp_details, levels_in), + prop, action, arg, mpctx); +} + +static int mp_property_colormatrix_output_range(m_option_t *prop, int action, + void *arg, MPContext *mpctx) +{ + return levels_property_helper(offsetof(struct mp_csp_details, levels_out), + prop, action, arg, mpctx); } static int mp_property_capture(m_option_t *prop, int action, @@ -2267,8 +2334,12 @@ static const m_option_t mp_properties[] = { M_OPT_RANGE, 0, 1, NULL }, { "deinterlace", mp_property_deinterlace, CONF_TYPE_FLAG, M_OPT_RANGE, 0, 1, NULL }, - { "yuv_colorspace", mp_property_yuv_colorspace, CONF_TYPE_INT, - M_OPT_RANGE, 0, 2, NULL }, + { "colormatrix", mp_property_colormatrix, &m_option_type_choice, + 0, 0, 0, "colormatrix" }, + { "colormatrix_input_range", mp_property_colormatrix_input_range, &m_option_type_choice, + 0, 0, 0, "colormatrix-input-range" }, + { "colormatrix_output_range", mp_property_colormatrix_output_range, &m_option_type_choice, + 0, 0, 0, "colormatrix-output-range" }, { "ontop", mp_property_ontop, CONF_TYPE_FLAG, M_OPT_RANGE, 0, 1, NULL }, { "rootwin", mp_property_rootwin, CONF_TYPE_FLAG, @@ -2430,7 +2501,9 @@ static struct property_osd_display { { "border", 0, -1, _("Border: %s") }, { "framedropping", 0, -1, _("Framedropping: %s") }, { "deinterlace", 0, -1, _("Deinterlace: %s") }, - { "yuv_colorspace", 0, -1, _("YUV colorspace: %s") }, + { "colormatrix", 0, -1, _("YUV colormatrix: %s") }, + { "colormatrix_input_range", 0, -1, _("YUV input range: %s") }, + { "colormatrix_output_range", 0, -1, _("RGB output range: %s") }, { "gamma", OSD_BRIGHTNESS, -1, _("Gamma") }, { "brightness", OSD_BRIGHTNESS, -1, _("Brightness") }, { "contrast", OSD_CONTRAST, -1, _("Contrast") }, @@ -2473,6 +2546,7 @@ static int show_property_osd(MPContext *mpctx, const char *pname) for (p = property_osd_display; p->name; p++) if (!strcmp(p->name, pname)) break; + if (!p->name) return -1; |