diff --git a/options/m_property.c b/options/m_property.c index 2ef5a62123..431e16a51a 100644 --- a/options/m_property.c +++ b/options/m_property.c @@ -36,6 +36,32 @@ #include "common/msg.h" #include "common/common.h" +static int m_property_multiply(struct mp_log *log, + const struct m_property *prop_list, + const char *property, double f, void *ctx) +{ + union m_option_value val = {0}; + struct m_option opt = {0}; + int r; + + r = m_property_do(log, prop_list, property, M_PROPERTY_GET_CONSTRICTED_TYPE, + &opt, ctx); + if (r != M_PROPERTY_OK) + return r; + assert(opt.type); + + if (!opt.type->multiply) + return M_PROPERTY_NOT_IMPLEMENTED; + + r = m_property_do(log, prop_list, property, M_PROPERTY_GET, &val, ctx); + if (r != M_PROPERTY_OK) + return r; + opt.type->multiply(&opt, &val, f); + r = m_property_do(log, prop_list, property, M_PROPERTY_SET, &val, ctx); + m_option_free(&opt, &val); + return r; +} + struct m_property *m_property_list_find(const struct m_property *list, const char *name) { @@ -107,6 +133,9 @@ int m_property_do(struct mp_log *log, const struct m_property *prop_list, struct mpv_node node = { .format = MPV_FORMAT_STRING, .u.string = arg }; return m_property_do(log, prop_list, name, M_PROPERTY_SET_NODE, &node, ctx); } + case M_PROPERTY_MULTIPLY: { + return m_property_multiply(log, prop_list, name, *(double *)arg, ctx); + } case M_PROPERTY_SWITCH: { if (!log) return M_PROPERTY_ERROR; diff --git a/options/m_property.h b/options/m_property.h index d71ec033aa..9ad4ccf9f6 100644 --- a/options/m_property.h +++ b/options/m_property.h @@ -79,6 +79,10 @@ enum mp_property_action { // arg: mpv_node* M_PROPERTY_SET_NODE, + // Multiply numeric property with a factor. + // arg: double* + M_PROPERTY_MULTIPLY, + // Pass down an action to a sub-property. // arg: struct m_property_action_arg* M_PROPERTY_KEY_ACTION, diff --git a/player/command.c b/player/command.c index b855f1dd96..e998ebecf3 100644 --- a/player/command.c +++ b/player/command.c @@ -4689,29 +4689,6 @@ static int *get_cmd_cycle_counter(struct MPContext *mpctx, char **args) return &cmd->cycle_counters[cmd->num_cycle_counters - 1].counter; } -static int mp_property_multiply(char *property, double f, struct MPContext *mpctx) -{ - union m_option_value val = {0}; - struct m_option opt = {0}; - int r; - - r = mp_property_do(property, M_PROPERTY_GET_CONSTRICTED_TYPE, &opt, mpctx); - if (r != M_PROPERTY_OK) - return r; - assert(opt.type); - - if (!opt.type->multiply) - return M_PROPERTY_NOT_IMPLEMENTED; - - r = mp_property_do(property, M_PROPERTY_GET, &val, mpctx); - if (r != M_PROPERTY_OK) - return r; - opt.type->multiply(&opt, &val, f); - r = mp_property_do(property, M_PROPERTY_SET, &val, mpctx); - m_option_free(&opt, &val); - return r; -} - static struct track *find_track_with_url(struct MPContext *mpctx, int type, const char *url) { @@ -4946,8 +4923,8 @@ int run_command(struct MPContext *mpctx, struct mp_cmd *cmd, struct mpv_node *re case MP_CMD_MULTIPLY: { char *property = cmd->args[0].v.s; - double f = cmd->args[1].v.d; - int r = mp_property_multiply(property, f, mpctx); + int r = mp_property_do(cmd->args[0].v.s, M_PROPERTY_MULTIPLY, + &cmd->args[1].v.d, mpctx); if (r == M_PROPERTY_OK || r == M_PROPERTY_UNAVAILABLE) { show_property_osd(mpctx, property, on_osd); @@ -4957,7 +4934,7 @@ int run_command(struct MPContext *mpctx, struct mp_cmd *cmd, struct mpv_node *re return -1; } else if (r <= 0) { set_osd_msg(mpctx, osdl, osd_duration, - "Failed to multiply property '%s' by %g", property, f); + "Failed to multiply property '%s'", property); return -1; } break;