mirror of
https://github.com/mpv-player/mpv
synced 2025-03-19 01:47:38 +00:00
options: remove deprecated sub-option handling for --vo and --ao
Long planned. Leads to some sanity. There still are some rather gross things. Especially g_groups is ugly, and a hack that can hopefully be removed. (There is a plan for it, but whether it's implemented depends on how much energy is left.)
This commit is contained in:
parent
98a257b3a8
commit
1a2319f3e4
@ -30,6 +30,10 @@ Interface changes
|
||||
- "audio-channels" (use "audio-params/channel-count")
|
||||
- "audio-format" (use "audio-codec-name")
|
||||
(the properties equivalent to the old semantics are in parentheses)
|
||||
- remove deprecated --vo and --ao sub-options (like --vo=opengl:...), and
|
||||
replace them with global options. A somewhat complete list can be found
|
||||
here: https://github.com/mpv-player/mpv/wiki/Option-replacement-list#mpv-0210
|
||||
- remove --vo-defaults and --ao-defaults as well
|
||||
- remove deprecated global sub-options (like -demuxer-rawaudio format=...),
|
||||
use flat options (like --demuxer-rawaudio-format=...)
|
||||
--- mpv 0.22.0 ---
|
||||
|
@ -10,11 +10,6 @@ syntax is:
|
||||
If the list has a trailing ',', mpv will fall back on drivers not contained
|
||||
in the list.
|
||||
|
||||
``--ao-defaults=<driver1[:parameter1:parameter2:...],driver2,...>``
|
||||
Set defaults for each driver.
|
||||
|
||||
Deprecated. No replacement.
|
||||
|
||||
.. note::
|
||||
|
||||
See ``--ao=help`` for a list of compiled-in audio output drivers. The
|
||||
|
@ -10,11 +10,6 @@ syntax is:
|
||||
If the list has a trailing ``,``, mpv will fall back on drivers not contained
|
||||
in the list.
|
||||
|
||||
``--vo-defaults=<driver1[:parameter1:parameter2:...],driver2,...>``
|
||||
Set defaults for each driver.
|
||||
|
||||
Deprecated. No replacement.
|
||||
|
||||
.. note::
|
||||
|
||||
See ``--vo=help`` for a list of compiled-in video output drivers.
|
||||
|
@ -112,8 +112,8 @@ static bool get_desc(struct m_obj_desc *dst, int index)
|
||||
.priv_size = ao->priv_size,
|
||||
.priv_defaults = ao->priv_defaults,
|
||||
.options = ao->options,
|
||||
.options_prefix = ao->options_prefix,
|
||||
.global_opts = ao->global_opts,
|
||||
.legacy_prefix = ao->legacy_prefix,
|
||||
.hidden = ao->encode,
|
||||
.p = ao,
|
||||
};
|
||||
@ -127,11 +127,12 @@ const struct m_obj_list ao_obj_list = {
|
||||
.allow_unknown_entries = true,
|
||||
.allow_trailer = true,
|
||||
.disallow_positional_parameters = true,
|
||||
.use_global_options = true,
|
||||
};
|
||||
|
||||
static struct ao *ao_alloc(bool probing, struct mpv_global *global,
|
||||
void (*wakeup_cb)(void *ctx), void *wakeup_ctx,
|
||||
char *name, char **args)
|
||||
char *name)
|
||||
{
|
||||
assert(wakeup_cb);
|
||||
|
||||
@ -155,12 +156,9 @@ static struct ao *ao_alloc(bool probing, struct mpv_global *global,
|
||||
.def_buffer = opts->audio_buffer,
|
||||
.client_name = talloc_strdup(ao, opts->audio_client_name),
|
||||
};
|
||||
struct m_config *config =
|
||||
m_config_from_obj_desc_and_args(ao, ao->log, global, &desc,
|
||||
name, opts->ao_defs, args);
|
||||
if (!config)
|
||||
ao->priv = m_config_group_from_desc(ao, ao->log, global, &desc, name);
|
||||
if (!ao->priv)
|
||||
goto error;
|
||||
ao->priv = config->optstruct;
|
||||
return ao;
|
||||
error:
|
||||
talloc_free(ao);
|
||||
@ -171,9 +169,9 @@ static struct ao *ao_init(bool probing, struct mpv_global *global,
|
||||
void (*wakeup_cb)(void *ctx), void *wakeup_ctx,
|
||||
struct encode_lavc_context *encode_lavc_ctx, int flags,
|
||||
int samplerate, int format, struct mp_chmap channels,
|
||||
char *dev, char *name, char **args)
|
||||
char *dev, char *name)
|
||||
{
|
||||
struct ao *ao = ao_alloc(probing, global, wakeup_cb, wakeup_ctx, name, args);
|
||||
struct ao *ao = ao_alloc(probing, global, wakeup_cb, wakeup_ctx, name);
|
||||
if (!ao)
|
||||
return NULL;
|
||||
ao->samplerate = samplerate;
|
||||
@ -206,7 +204,7 @@ static struct ao *ao_init(bool probing, struct mpv_global *global,
|
||||
talloc_free(ao);
|
||||
return ao_init(probing, global, wakeup_cb, wakeup_ctx,
|
||||
encode_lavc_ctx, flags, samplerate, format, channels,
|
||||
rdevice, redirect, NULL);
|
||||
rdevice, redirect);
|
||||
}
|
||||
goto fail;
|
||||
}
|
||||
@ -313,8 +311,7 @@ struct ao *ao_init_best(struct mpv_global *global,
|
||||
mp_verbose(log, "Using preferred device '%s'\n", dev);
|
||||
}
|
||||
ao = ao_init(probing, global, wakeup_cb, wakeup_ctx, encode_lavc_ctx,
|
||||
init_flags, samplerate, format, channels, dev,
|
||||
entry->name, entry->attribs);
|
||||
init_flags, samplerate, format, channels, dev, entry->name);
|
||||
if (ao)
|
||||
break;
|
||||
if (!probing)
|
||||
@ -571,7 +568,7 @@ struct ao_device_list *ao_hotplug_get_device_list(struct ao_hotplug *hp)
|
||||
break; // don't add unsafe/special entries
|
||||
|
||||
struct ao *ao = ao_alloc(true, hp->global, hp->wakeup_cb, hp->wakeup_ctx,
|
||||
(char *)d->name, NULL);
|
||||
(char *)d->name);
|
||||
if (!ao)
|
||||
continue;
|
||||
|
||||
|
@ -1196,15 +1196,5 @@ const struct ao_driver audio_out_alsa = {
|
||||
.wakeup = ao_wakeup_poll,
|
||||
.list_devs = list_devs,
|
||||
.priv_size = sizeof(struct priv),
|
||||
.options = (const struct m_option[]) {
|
||||
OPT_SUBOPT_LEGACY("device", "alsa-device"),
|
||||
OPT_SUBOPT_LEGACY("resample", "alsa-resample"),
|
||||
OPT_SUBOPT_LEGACY("mixer-device", "alsa-mixer-device"),
|
||||
OPT_SUBOPT_LEGACY("mixer-name", "alsa-mixer-name"),
|
||||
OPT_SUBOPT_LEGACY("mixer-index", "alsa-mixer-index"),
|
||||
OPT_SUBOPT_LEGACY("non-interleaved", "alsa-non-interleaved"),
|
||||
OPT_SUBOPT_LEGACY("ignore-chmap", "alsa-ignore-chmap"),
|
||||
{0}
|
||||
},
|
||||
.global_opts = &ao_alsa_conf,
|
||||
};
|
||||
|
@ -195,7 +195,4 @@ const struct ao_driver audio_out_audiounit = {
|
||||
.pause = stop,
|
||||
.resume = start,
|
||||
.priv_size = sizeof(struct priv),
|
||||
.options = (const struct m_option[]){
|
||||
{0}
|
||||
},
|
||||
};
|
||||
|
@ -39,7 +39,6 @@ struct priv {
|
||||
AudioStreamID original_asbd_stream;
|
||||
|
||||
int change_physical_format;
|
||||
int exclusive;
|
||||
};
|
||||
|
||||
static int64_t ca_get_hardware_latency(struct ao *ao) {
|
||||
@ -143,9 +142,7 @@ static int init(struct ao *ao)
|
||||
{
|
||||
struct priv *p = ao->priv;
|
||||
|
||||
p->exclusive |= ao->init_flags & AO_INIT_EXCLUSIVE;
|
||||
|
||||
if (!af_fmt_is_pcm(ao->format) || p->exclusive) {
|
||||
if (!af_fmt_is_pcm(ao->format) || (ao->init_flags & AO_INIT_EXCLUSIVE)) {
|
||||
MP_VERBOSE(ao, "redirecting to coreaudio_exclusive\n");
|
||||
ao->redirect = "coreaudio_exclusive";
|
||||
return CONTROL_ERROR;
|
||||
@ -429,9 +426,7 @@ const struct ao_driver audio_out_coreaudio = {
|
||||
.priv_size = sizeof(struct priv),
|
||||
.options = (const struct m_option[]){
|
||||
OPT_FLAG("change-physical-format", change_physical_format, 0),
|
||||
OPT_FLAG("exclusive", exclusive, 0,
|
||||
.deprecation_message = "use --audio-exclusive"),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "coreaudio",
|
||||
.options_prefix = "coreaudio",
|
||||
};
|
||||
|
@ -246,13 +246,5 @@ const struct ao_driver audio_out_jack = {
|
||||
.uninit = uninit,
|
||||
.resume = resume,
|
||||
.priv_size = sizeof(struct priv),
|
||||
.options = (const struct m_option[]) {
|
||||
OPT_SUBOPT_LEGACY("port", "jack-port"),
|
||||
OPT_SUBOPT_LEGACY("name", "jack-name"),
|
||||
OPT_SUBOPT_LEGACY("autostart", "jack-autostart"),
|
||||
OPT_SUBOPT_LEGACY("connect", "jack-connect"),
|
||||
OPT_SUBOPT_LEGACY("std-channel-layout", "jack-std-channel-layout"),
|
||||
{0}
|
||||
},
|
||||
.global_opts = &ao_jack_conf,
|
||||
};
|
||||
|
@ -241,5 +241,5 @@ const struct ao_driver audio_out_null = {
|
||||
OPT_CHANNELS("channel-layouts", channel_layouts, 0),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "ao-null",
|
||||
.options_prefix = "ao-null",
|
||||
};
|
||||
|
@ -374,5 +374,5 @@ const struct ao_driver audio_out_openal = {
|
||||
DEVICE_OPT_DEPRECATION),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "ao-openal",
|
||||
.options_prefix = "ao-openal",
|
||||
};
|
||||
|
@ -246,5 +246,5 @@ const struct ao_driver audio_out_opensles = {
|
||||
OPT_INTRANGE("sample-rate", cfg_sample_rate, 0, 1000, 100000),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "opensles",
|
||||
.options_prefix = "opensles",
|
||||
};
|
||||
|
@ -653,5 +653,5 @@ const struct ao_driver audio_out_oss = {
|
||||
OPT_STRING("mixer-channel", cfg_oss_mixer_channel, 0),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "oss",
|
||||
.options_prefix = "oss",
|
||||
};
|
||||
|
@ -224,5 +224,5 @@ const struct ao_driver audio_out_pcm = {
|
||||
OPT_FLAG("append", append, 0),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "ao-pcm",
|
||||
.options_prefix = "ao-pcm",
|
||||
};
|
||||
|
@ -841,5 +841,5 @@ const struct ao_driver audio_out_pulse = {
|
||||
OPT_FLAG("latency-hacks", cfg_latency_hacks, 0),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "pulse",
|
||||
.options_prefix = "pulse",
|
||||
};
|
||||
|
@ -162,6 +162,6 @@ const struct ao_driver audio_out_rsound = {
|
||||
.deprecation_message = "request --audio-device support on issue tracker"),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "rsound",
|
||||
.options_prefix = "rsound",
|
||||
};
|
||||
|
||||
|
@ -212,5 +212,5 @@ const struct ao_driver audio_out_sdl = {
|
||||
OPT_FLOAT("buflen", buflen, 0),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "sdl",
|
||||
.options_prefix = "sdl",
|
||||
};
|
||||
|
@ -324,5 +324,5 @@ const struct ao_driver audio_out_sndio = {
|
||||
DEVICE_OPT_DEPRECATION),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "ao-sndio",
|
||||
.options_prefix = "ao-sndio",
|
||||
};
|
||||
|
@ -496,11 +496,4 @@ const struct ao_driver audio_out_wasapi = {
|
||||
.hotplug_init = hotplug_init,
|
||||
.hotplug_uninit = hotplug_uninit,
|
||||
.priv_size = sizeof(wasapi_state),
|
||||
.options = (const struct m_option[]) {
|
||||
OPT_FLAG("exclusive", opt_exclusive, 0,
|
||||
.deprecation_message = "use --audio-exclusive"),
|
||||
OPT_STRING("device", opt_device, 0, DEVICE_OPT_DEPRECATION),
|
||||
{NULL},
|
||||
},
|
||||
.legacy_prefix = "ao-wasapi",
|
||||
};
|
||||
|
@ -92,8 +92,6 @@ typedef struct wasapi_state {
|
||||
|
||||
// ao options
|
||||
int opt_exclusive;
|
||||
int opt_list;
|
||||
char *opt_device;
|
||||
|
||||
// format info
|
||||
WAVEFORMATEXTENSIBLE format;
|
||||
|
@ -858,10 +858,7 @@ static LPWSTR select_device(struct mp_log *l, struct device_desc *d)
|
||||
bstr wasapi_get_specified_device_string(struct ao *ao)
|
||||
{
|
||||
struct wasapi_state *state = ao->priv;
|
||||
bstr device = bstr_strip(bstr0(state->opt_device));
|
||||
if (!device.len)
|
||||
device = bstr_strip(bstr0(ao->device));
|
||||
return device;
|
||||
return bstr_strip(bstr0(ao->device));
|
||||
}
|
||||
|
||||
LPWSTR wasapi_find_deviceID(struct ao *ao)
|
||||
|
@ -182,8 +182,8 @@ struct ao_driver {
|
||||
int priv_size;
|
||||
const void *priv_defaults;
|
||||
const struct m_option *options;
|
||||
const char *options_prefix;
|
||||
const struct m_sub_options *global_opts;
|
||||
const char *legacy_prefix;
|
||||
};
|
||||
|
||||
// These functions can be called by AOs.
|
||||
|
@ -39,6 +39,7 @@
|
||||
|
||||
#include "m_config.h"
|
||||
#include "options/m_option.h"
|
||||
#include "common/common.h"
|
||||
#include "common/global.h"
|
||||
#include "common/msg.h"
|
||||
#include "common/msg_control.h"
|
||||
@ -268,6 +269,39 @@ struct m_config *m_config_from_obj_desc_noalloc(void *talloc_ctx,
|
||||
return m_config_new(talloc_ctx, log, 0, desc->priv_defaults, desc->options);
|
||||
}
|
||||
|
||||
static struct m_config_group *find_group(struct mpv_global *global,
|
||||
const struct m_option *cfg)
|
||||
{
|
||||
struct m_config_shadow *shadow = global->config;
|
||||
struct m_config *root = shadow->root;
|
||||
|
||||
for (int n = 0; n < root->num_groups; n++) {
|
||||
if (cfg && root->groups[n].group && root->groups[n].group->opts == cfg)
|
||||
return &root->groups[n];
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Allocate a priv struct that is backed by global options (like AOs and VOs,
|
||||
// anything that uses m_obj_list.use_global_options == true).
|
||||
// The result contains a snapshot of the current option values of desc->options.
|
||||
// For convenience, desc->options can be NULL; then priv struct is allocated
|
||||
// with just zero (or priv_defaults if set).
|
||||
void *m_config_group_from_desc(void *ta_parent, struct mp_log *log,
|
||||
struct mpv_global *global, struct m_obj_desc *desc, const char *name)
|
||||
{
|
||||
struct m_config_group *group = find_group(global, desc->options);
|
||||
if (group) {
|
||||
return mp_get_config_group(ta_parent, global, group->group);
|
||||
} else {
|
||||
void *d = talloc_zero_size(ta_parent, desc->priv_size);
|
||||
if (desc->priv_defaults)
|
||||
memcpy(d, desc->priv_defaults, desc->priv_size);
|
||||
return d;
|
||||
}
|
||||
}
|
||||
|
||||
static struct m_config_option *m_config_find_negation_opt(struct m_config *config,
|
||||
struct bstr *name);
|
||||
|
||||
@ -277,40 +311,8 @@ static int m_config_set_obj_params(struct m_config *config, struct mp_log *log,
|
||||
{
|
||||
for (int n = 0; args && args[n * 2 + 0]; n++) {
|
||||
bstr opt = bstr0(args[n * 2 + 0]);
|
||||
const char *val = args[n * 2 + 1];
|
||||
struct m_config_option *co = m_config_get_co(config, opt);
|
||||
if (!co) {
|
||||
co = m_config_find_negation_opt(config, &opt);
|
||||
if (!co)
|
||||
continue;
|
||||
|
||||
if (val && val[0])
|
||||
return -1; // no parameter allowed
|
||||
|
||||
val = "no";
|
||||
}
|
||||
struct m_config *target = config;
|
||||
bool is_legacy = co->opt->type == &m_option_type_subopt_legacy;
|
||||
bool force_legacy = !!desc->legacy_prefix;
|
||||
if (is_legacy || force_legacy) {
|
||||
// Legacy: redirect deprecated sub-options to global ones.
|
||||
char tmp[100];
|
||||
const char *newopt;
|
||||
if (is_legacy) {
|
||||
newopt = co->opt->priv;
|
||||
} else {
|
||||
snprintf(tmp, sizeof(tmp), "%s-%.*s", desc->legacy_prefix,
|
||||
BSTR_P(opt));
|
||||
newopt = tmp;
|
||||
}
|
||||
assert(global);
|
||||
target = mp_get_root_config(global);
|
||||
mp_warn(log, "Using suboptions is deprecated. Use the global '--%s' "
|
||||
"option instead of '%.*s' suboption.\n", newopt,
|
||||
BSTR_P(opt));
|
||||
opt = bstr0(newopt);
|
||||
}
|
||||
if (m_config_set_option(target, opt, bstr0(val)) < 0)
|
||||
bstr val = bstr0(args[n * 2 + 1]);
|
||||
if (m_config_set_option(config, opt, val) < 0)
|
||||
return -1;
|
||||
}
|
||||
|
||||
@ -334,21 +336,6 @@ struct m_config *m_config_from_obj_desc_and_args(void *ta_parent,
|
||||
if (m_config_set_obj_params(config, log, global, desc, args) < 0)
|
||||
goto error;
|
||||
|
||||
if (desc->legacy_prefix) {
|
||||
assert(global);
|
||||
struct m_config *root = mp_get_root_config(global);
|
||||
// In this mode, the AO/VO will still access the options via its priv
|
||||
// struct (like with real sub-options). We have to copy them over.
|
||||
for (int n = 0; n < config->num_opts; n++) {
|
||||
struct m_config_option *co = &config->opts[n];
|
||||
char opt[100];
|
||||
snprintf(opt, sizeof(opt), "%s-%s", desc->legacy_prefix, co->name);
|
||||
struct m_config_option *g = m_config_get_co_raw(root, bstr0(opt));
|
||||
assert(g);
|
||||
m_option_copy(co->opt, co->data, g->data);
|
||||
}
|
||||
}
|
||||
|
||||
return config;
|
||||
error:
|
||||
talloc_free(config);
|
||||
@ -457,34 +444,83 @@ static void add_sub_options(struct m_config *config,
|
||||
};
|
||||
|
||||
struct m_config_option next = {
|
||||
.name = parent ? parent->name : "",
|
||||
.name = "",
|
||||
.group = group,
|
||||
};
|
||||
if (parent && parent->name && parent->name[0])
|
||||
next.name = parent->name;
|
||||
if (subopts->prefix && subopts->prefix[0]) {
|
||||
assert(next.name);
|
||||
next.name = subopts->prefix;
|
||||
}
|
||||
add_options(config, &next, new_optstruct, new_optstruct_def, subopts->opts);
|
||||
}
|
||||
|
||||
static void add_global_subopts(struct m_config *config,
|
||||
const struct m_obj_list *list)
|
||||
#define MAX_VO_AO 16
|
||||
|
||||
struct group_entry {
|
||||
const struct m_obj_list *entry;
|
||||
struct m_sub_options subs[MAX_VO_AO];
|
||||
bool initialized;
|
||||
};
|
||||
|
||||
static struct group_entry g_groups[2]; // limited by max. m_obj_list overall
|
||||
static int g_num_groups = 0;
|
||||
static pthread_mutex_t g_group_mutex = PTHREAD_MUTEX_INITIALIZER;
|
||||
|
||||
static const struct m_sub_options *get_cached_group(const struct m_obj_list *list,
|
||||
int n, struct m_sub_options *v)
|
||||
{
|
||||
pthread_mutex_lock(&g_group_mutex);
|
||||
|
||||
struct group_entry *group = NULL;
|
||||
for (int i = 0; i < g_num_groups; i++) {
|
||||
if (g_groups[i].entry == list) {
|
||||
group = &g_groups[i];
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!group) {
|
||||
assert(g_num_groups < MP_ARRAY_SIZE(g_groups));
|
||||
group = &g_groups[g_num_groups++];
|
||||
group->entry = list;
|
||||
}
|
||||
|
||||
if (!group->initialized) {
|
||||
if (!v) {
|
||||
n = -1;
|
||||
group->initialized = true;
|
||||
} else {
|
||||
assert(n < MAX_VO_AO); // simply increase this if it fails
|
||||
group->subs[n] = *v;
|
||||
}
|
||||
}
|
||||
|
||||
pthread_mutex_unlock(&g_group_mutex);
|
||||
|
||||
return n >= 0 ? &group->subs[n] : NULL;
|
||||
}
|
||||
|
||||
static void init_obj_settings_list(struct m_config *config,
|
||||
const struct m_obj_list *list)
|
||||
{
|
||||
struct m_obj_desc desc;
|
||||
for (int n = 0; ; n++) {
|
||||
if (!list->get_desc(&desc, n))
|
||||
if (!list->get_desc(&desc, n)) {
|
||||
if (list->use_global_options)
|
||||
get_cached_group(list, n, NULL);
|
||||
break;
|
||||
}
|
||||
if (desc.global_opts)
|
||||
add_sub_options(config, NULL, desc.global_opts);
|
||||
if (desc.legacy_prefix && desc.options) {
|
||||
// Legacy: auto-add sub-options as global options (using the prefix).
|
||||
struct m_config_option parent = {
|
||||
.name = desc.legacy_prefix,
|
||||
.group = 0,
|
||||
};
|
||||
struct m_sub_options *conf = talloc(config, struct m_sub_options);
|
||||
*conf = (struct m_sub_options){
|
||||
if (list->use_global_options && desc.options) {
|
||||
struct m_sub_options conf = {
|
||||
.prefix = desc.options_prefix,
|
||||
.opts = desc.options,
|
||||
.defaults = desc.priv_defaults,
|
||||
.size = desc.priv_size,
|
||||
};
|
||||
add_sub_options(config, &parent, conf);
|
||||
add_sub_options(config, NULL, get_cached_group(list, n, &conf));
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -560,9 +596,8 @@ static void m_config_add_option(struct m_config *config,
|
||||
init_opt_inplace(arg, co.data, co.default_data);
|
||||
}
|
||||
|
||||
// (The deprecation_message check is a hack to exclude --vo-defaults etc.)
|
||||
if (arg->type == &m_option_type_obj_settings_list && !arg->deprecation_message)
|
||||
add_global_subopts(config, (const struct m_obj_list *)arg->priv);
|
||||
if (arg->type == &m_option_type_obj_settings_list)
|
||||
init_obj_settings_list(config, (const struct m_obj_list *)arg->priv);
|
||||
|
||||
if (arg->name[0]) // no own name -> hidden
|
||||
MP_TARRAY_APPEND(config, config->opts, config->num_opts, co);
|
||||
|
@ -134,6 +134,9 @@ struct m_config *m_config_from_obj_desc_and_args(void *ta_parent,
|
||||
struct mp_log *log, struct mpv_global *global, struct m_obj_desc *desc,
|
||||
const char *name, struct m_obj_settings *defaults, char **args);
|
||||
|
||||
void *m_config_group_from_desc(void *ta_parent, struct mp_log *log,
|
||||
struct mpv_global *global, struct m_obj_desc *desc, const char *name);
|
||||
|
||||
// Make sure the option is backed up. If it's already backed up, do nothing.
|
||||
// All backed up options can be restored with m_config_restore_backups().
|
||||
void m_config_backup_opt(struct m_config *config, const char *opt);
|
||||
|
@ -2719,7 +2719,8 @@ static int get_obj_param(struct mp_log *log, bstr opt_name, bstr obj_name,
|
||||
static int m_obj_parse_sub_config(struct mp_log *log, struct bstr opt_name,
|
||||
struct bstr name, struct bstr *pstr,
|
||||
struct m_config *config, int flags, bool nopos,
|
||||
struct m_obj_desc *desc, char ***ret)
|
||||
struct m_obj_desc *desc,
|
||||
const struct m_obj_list *list, char ***ret)
|
||||
{
|
||||
int nold = 0;
|
||||
char **args = NULL;
|
||||
@ -2737,6 +2738,16 @@ static int m_obj_parse_sub_config(struct mp_log *log, struct bstr opt_name,
|
||||
r = split_subconf(log, opt_name, pstr, &fname, &fval);
|
||||
if (r < 0)
|
||||
goto exit;
|
||||
|
||||
if (list->use_global_options) {
|
||||
mp_err(log, "Option %.*s: this option does not accept sub-options.\n",
|
||||
BSTR_P(opt_name));
|
||||
mp_err(log, "Sub-options for --vo and --ao were removed from mpv in "
|
||||
"release 0.23.0.\nSee https://0x0.st/uM for details.\n");
|
||||
r = M_OPT_INVALID;
|
||||
goto exit;
|
||||
}
|
||||
|
||||
if (bstr_equals0(fname, "help"))
|
||||
goto print_help;
|
||||
r = get_obj_param(log, opt_name, name, config, fname, fval, flags,
|
||||
@ -2831,7 +2842,7 @@ static int parse_obj_settings(struct mp_log *log, struct bstr opt,
|
||||
struct m_config *config = m_config_from_obj_desc_noalloc(NULL, log, &desc);
|
||||
bstr s = bstr0(desc.init_options);
|
||||
m_obj_parse_sub_config(log, opt, str, &s, config,
|
||||
M_SETOPT_CHECK_ONLY, nopos, NULL, &plist);
|
||||
M_SETOPT_CHECK_ONLY, nopos, NULL, list, &plist);
|
||||
assert(s.len == 0);
|
||||
talloc_free(config);
|
||||
}
|
||||
@ -2841,7 +2852,7 @@ static int parse_obj_settings(struct mp_log *log, struct bstr opt,
|
||||
if (!skip)
|
||||
config = m_config_from_obj_desc_noalloc(NULL, log, &desc);
|
||||
r = m_obj_parse_sub_config(log, opt, str, pstr, config,
|
||||
M_SETOPT_CHECK_ONLY, nopos, &desc,
|
||||
M_SETOPT_CHECK_ONLY, nopos, &desc, list,
|
||||
_ret ? &plist : NULL);
|
||||
talloc_free(config);
|
||||
if (r < 0)
|
||||
|
@ -117,6 +117,8 @@ struct m_obj_desc {
|
||||
const void *priv_defaults;
|
||||
// Options which refer to members in the private struct
|
||||
const struct m_option *options;
|
||||
// Prefix for each of the above options (none if NULL).
|
||||
const char *options_prefix;
|
||||
// For free use by the implementer of m_obj_list.get_desc
|
||||
const void *p;
|
||||
// If not NULL, options which should be set before applying other options.
|
||||
@ -132,10 +134,6 @@ struct m_obj_desc {
|
||||
const char *replaced_name;
|
||||
// For convenience: these are added as global command-line options.
|
||||
const struct m_sub_options *global_opts;
|
||||
// Evil hack to essentially force-move .options to global_opts. All options
|
||||
// will be added as global options with the given prefix, and using
|
||||
// sub-options will be treated as deprecated and redirected.
|
||||
const char *legacy_prefix;
|
||||
};
|
||||
|
||||
// Extra definition needed for \ref m_option_type_obj_settings_list options.
|
||||
@ -151,6 +149,8 @@ struct m_obj_list {
|
||||
bool allow_unknown_entries;
|
||||
// This helps with confusing error messages if unknown flag options are used.
|
||||
bool disallow_positional_parameters;
|
||||
// Each sub-item is backed by global options (for AOs and VOs).
|
||||
bool use_global_options;
|
||||
};
|
||||
|
||||
// Find entry by name
|
||||
@ -188,6 +188,7 @@ typedef int (*m_opt_string_validate_fn)(struct mp_log *log, const m_option_t *op
|
||||
|
||||
// m_option.priv points to this if OPT_SUBSTRUCT is used
|
||||
struct m_sub_options {
|
||||
const char *prefix;
|
||||
const struct m_option *opts;
|
||||
size_t size;
|
||||
const void *defaults;
|
||||
@ -714,12 +715,6 @@ extern const char m_option_path_separator;
|
||||
.type = &m_option_type_subconfig, \
|
||||
.priv = (void*)&subconf)
|
||||
|
||||
// Same as above, but for legacy suboption usage, which have no associated
|
||||
// field (no actual data anywhere).
|
||||
#define OPT_SUBSTRUCT_LEGACY(optname, subconf) \
|
||||
{.name = optname, .offset = -1, .type = &m_option_type_subconfig, \
|
||||
.priv = (void*)&subconf}
|
||||
|
||||
// Provide a another name for the option.
|
||||
#define OPT_ALIAS(optname, newname) \
|
||||
{.name = optname, .type = &m_option_type_alias, .priv = newname, \
|
||||
|
@ -150,8 +150,6 @@ const struct m_sub_options stream_cache_conf = {
|
||||
|
||||
static const m_option_t mp_vo_opt_list[] = {
|
||||
OPT_SETTINGSLIST("vo", video_driver_list, 0, &vo_obj_list, ),
|
||||
OPT_SETTINGSLIST("vo-defaults", vo_defs, 0, &vo_obj_list,
|
||||
.deprecation_message = "deprecated, use global options"),
|
||||
OPT_CHOICE_C("hwdec-preload", hwdec_preload_api, 0, mp_hwdec_names),
|
||||
OPT_SUBSTRUCT("sws", sws_opts, sws_conf, 0),
|
||||
OPT_FLAG("taskbar-progress", taskbar_progress, 0),
|
||||
@ -510,8 +508,6 @@ const m_option_t mp_opts[] = {
|
||||
|
||||
//---------------------- libao/libvo options ------------------------
|
||||
OPT_SETTINGSLIST("ao", audio_driver_list, 0, &ao_obj_list, ),
|
||||
OPT_SETTINGSLIST("ao-defaults", ao_defs, 0, &ao_obj_list,
|
||||
.deprecation_message = "deprecated, use global options"),
|
||||
OPT_STRING("audio-device", audio_device, UPDATE_AUDIO),
|
||||
OPT_FLAG("audio-exclusive", audio_exclusive, UPDATE_AUDIO),
|
||||
OPT_STRING("audio-client-name", audio_client_name, UPDATE_AUDIO),
|
||||
|
@ -7,7 +7,7 @@
|
||||
#include "common/common.h"
|
||||
|
||||
typedef struct mp_vo_opts {
|
||||
struct m_obj_settings *video_driver_list, *vo_defs;
|
||||
struct m_obj_settings *video_driver_list;
|
||||
|
||||
int taskbar_progress;
|
||||
int ontop;
|
||||
@ -90,7 +90,7 @@ typedef struct MPOpts {
|
||||
|
||||
int auto_load_scripts;
|
||||
|
||||
struct m_obj_settings *audio_driver_list, *ao_defs;
|
||||
struct m_obj_settings *audio_driver_list;
|
||||
char *audio_device;
|
||||
int audio_exclusive;
|
||||
char *audio_client_name;
|
||||
|
@ -428,95 +428,6 @@ const struct m_sub_options gl_video_conf = {
|
||||
.change_flags = UPDATE_RENDERER,
|
||||
};
|
||||
|
||||
#define LEGACY_SCALER_OPTS(n) \
|
||||
OPT_SUBOPT_LEGACY(n, n), \
|
||||
OPT_SUBOPT_LEGACY(n"-param1", n"-param1"), \
|
||||
OPT_SUBOPT_LEGACY(n"-param2", n"-param2"), \
|
||||
OPT_SUBOPT_LEGACY(n"-blur", n"-blur"), \
|
||||
OPT_SUBOPT_LEGACY(n"-wparam", n"-wparam"), \
|
||||
OPT_SUBOPT_LEGACY(n"-clamp", n"-clamp"), \
|
||||
OPT_SUBOPT_LEGACY(n"-radius", n"-radius"), \
|
||||
OPT_SUBOPT_LEGACY(n"-antiring", n"-antiring"), \
|
||||
OPT_SUBOPT_LEGACY(n"-window", n"-window")
|
||||
|
||||
const struct m_sub_options gl_video_conf_legacy = {
|
||||
.opts = (const m_option_t[]) {
|
||||
OPT_SUBOPT_LEGACY("dumb-mode", "opengl-dumb-mode"),
|
||||
OPT_SUBOPT_LEGACY("gamma", "opengl-gamma"),
|
||||
OPT_SUBOPT_LEGACY("gamma-auto", "gamma-auto"),
|
||||
OPT_SUBOPT_LEGACY("target-prim", "target-prim"),
|
||||
OPT_SUBOPT_LEGACY("target-trc", "target-trc"),
|
||||
OPT_SUBOPT_LEGACY("target-brightness", "target-brightness"),
|
||||
OPT_SUBOPT_LEGACY("hdr-tone-mapping", "hdr-tone-mapping"),
|
||||
OPT_SUBOPT_LEGACY("tone-mapping-param", "tone-mapping-param"),
|
||||
OPT_SUBOPT_LEGACY("pbo", "opengl-pbo"),
|
||||
LEGACY_SCALER_OPTS("scale"),
|
||||
LEGACY_SCALER_OPTS("dscale"),
|
||||
LEGACY_SCALER_OPTS("cscale"),
|
||||
LEGACY_SCALER_OPTS("tscale"),
|
||||
OPT_SUBOPT_LEGACY("scaler-lut-size", "scaler-lut-size"),
|
||||
OPT_SUBOPT_LEGACY("scaler-resizes-only", "scaler-resizes-only"),
|
||||
OPT_SUBOPT_LEGACY("linear-scaling", "linear-scaling"),
|
||||
OPT_SUBOPT_LEGACY("correct-downscaling", "correct-downscaling"),
|
||||
OPT_SUBOPT_LEGACY("sigmoid-upscaling", "sigmoid-upscaling"),
|
||||
OPT_SUBOPT_LEGACY("sigmoid-center", "sigmoid-center"),
|
||||
OPT_SUBOPT_LEGACY("sigmoid-slope", "sigmoid-slope"),
|
||||
OPT_SUBOPT_LEGACY("fbo-format", "opengl-fbo-format"),
|
||||
OPT_SUBOPT_LEGACY("dither-depth", "dither-depth"),
|
||||
OPT_SUBOPT_LEGACY("dither", "dither"),
|
||||
OPT_SUBOPT_LEGACY("dither-size-fruit", "dither-size-fruit"),
|
||||
OPT_SUBOPT_LEGACY("temporal-dither", "temporal-dither"),
|
||||
OPT_SUBOPT_LEGACY("temporal-dither-period", "temporal-dither-period"),
|
||||
OPT_SUBOPT_LEGACY("alpha", "alpha"),
|
||||
OPT_SUBOPT_LEGACY("rectangle-textures", "opengl-rectangle-textures"),
|
||||
OPT_SUBOPT_LEGACY("background", "background"),
|
||||
OPT_SUBOPT_LEGACY("interpolation", "interpolation"),
|
||||
OPT_SUBOPT_LEGACY("interpolation-threshold", "interpolation-threshold"),
|
||||
OPT_SUBOPT_LEGACY("blend-subtitles", "blend-subtitles"),
|
||||
OPT_SUBOPT_LEGACY("user-shaders", "opengl-shaders"),
|
||||
OPT_SUBOPT_LEGACY("deband", "deband"),
|
||||
OPT_SUBOPT_LEGACY("deband-iterations", "deband-iterations"),
|
||||
OPT_SUBOPT_LEGACY("deband-threshold", "deband-threshold"),
|
||||
OPT_SUBOPT_LEGACY("deband-range", "deband-range"),
|
||||
OPT_SUBOPT_LEGACY("deband-grain", "deband-grain"),
|
||||
OPT_SUBOPT_LEGACY("sharpen", "sharpen"),
|
||||
OPT_SUBOPT_LEGACY("icc-profile", "icc-profile"),
|
||||
OPT_SUBOPT_LEGACY("icc-profile-auto", "icc-profile-auto"),
|
||||
OPT_SUBOPT_LEGACY("icc-cache-dir", "icc-cache-dir"),
|
||||
OPT_SUBOPT_LEGACY("icc-intent", "icc-intent"),
|
||||
OPT_SUBOPT_LEGACY("icc-contrast", "icc-contrast"),
|
||||
OPT_SUBOPT_LEGACY("3dlut-size", "icc-3dlut-size"),
|
||||
|
||||
OPT_REMOVED("approx-gamma", "this is always enabled now"),
|
||||
OPT_REMOVED("cscale-down", "chroma is never downscaled"),
|
||||
OPT_REMOVED("scale-sep", "this is set automatically whenever sane"),
|
||||
OPT_REMOVED("indirect", "this is set automatically whenever sane"),
|
||||
OPT_REMOVED("srgb", "use target-prim=bt709:target-trc=srgb instead"),
|
||||
OPT_REMOVED("source-shader", "use :deband to enable debanding"),
|
||||
OPT_REMOVED("prescale-luma", "use opengl-shaders for prescaling"),
|
||||
OPT_REMOVED("scale-shader", "use opengl-shaders instead"),
|
||||
OPT_REMOVED("pre-shaders", "use opengl-shaders instead"),
|
||||
OPT_REMOVED("post-shaders", "use opengl-shaders instead"),
|
||||
|
||||
OPT_SUBOPT_LEGACY("lscale", "scale"),
|
||||
OPT_SUBOPT_LEGACY("lscale-down", "scale-down"),
|
||||
OPT_SUBOPT_LEGACY("lparam1", "scale-param1"),
|
||||
OPT_SUBOPT_LEGACY("lparam2", "scale-param2"),
|
||||
OPT_SUBOPT_LEGACY("lradius", "scale-radius"),
|
||||
OPT_SUBOPT_LEGACY("lantiring", "scale-antiring"),
|
||||
OPT_SUBOPT_LEGACY("cparam1", "cscale-param1"),
|
||||
OPT_SUBOPT_LEGACY("cparam2", "cscale-param2"),
|
||||
OPT_SUBOPT_LEGACY("cradius", "cscale-radius"),
|
||||
OPT_SUBOPT_LEGACY("cantiring", "cscale-antiring"),
|
||||
OPT_SUBOPT_LEGACY("smoothmotion", "interpolation"),
|
||||
OPT_SUBOPT_LEGACY("smoothmotion-threshold", "tscale-param1"),
|
||||
OPT_SUBOPT_LEGACY("scale-down", "dscale"),
|
||||
OPT_SUBOPT_LEGACY("fancy-downscaling", "correct-downscaling"),
|
||||
|
||||
{0}
|
||||
},
|
||||
};
|
||||
|
||||
static void uninit_rendering(struct gl_video *p);
|
||||
static void uninit_scaler(struct gl_video *p, struct scaler *scaler);
|
||||
static void check_gl_features(struct gl_video *p);
|
||||
|
@ -137,7 +137,6 @@ struct gl_video_opts {
|
||||
};
|
||||
|
||||
extern const struct m_sub_options gl_video_conf;
|
||||
extern const struct m_sub_options gl_video_conf_legacy;
|
||||
|
||||
struct gl_video;
|
||||
struct vo_frame;
|
||||
|
@ -176,8 +176,8 @@ static bool get_desc(struct m_obj_desc *dst, int index)
|
||||
.priv_size = vo->priv_size,
|
||||
.priv_defaults = vo->priv_defaults,
|
||||
.options = vo->options,
|
||||
.options_prefix = vo->options_prefix,
|
||||
.global_opts = vo->global_opts,
|
||||
.legacy_prefix = vo->legacy_prefix,
|
||||
.hidden = vo->encode || !strcmp(vo->name, "opengl-cb"),
|
||||
.p = vo,
|
||||
};
|
||||
@ -196,6 +196,7 @@ const struct m_obj_list vo_obj_list = {
|
||||
.allow_unknown_entries = true,
|
||||
.allow_trailer = true,
|
||||
.disallow_positional_parameters = true,
|
||||
.use_global_options = true,
|
||||
};
|
||||
|
||||
static void dispatch_wakeup_cb(void *ptr)
|
||||
@ -214,7 +215,7 @@ static void dealloc_vo(struct vo *vo)
|
||||
}
|
||||
|
||||
static struct vo *vo_create(bool probing, struct mpv_global *global,
|
||||
struct vo_extra *ex, char *name, char **args)
|
||||
struct vo_extra *ex, char *name)
|
||||
{
|
||||
assert(ex->wakeup_cb);
|
||||
|
||||
@ -254,11 +255,9 @@ static struct vo *vo_create(bool probing, struct mpv_global *global,
|
||||
mp_input_set_mouse_transform(vo->input_ctx, NULL, NULL);
|
||||
if (vo->driver->encode != !!vo->encode_lavc_ctx)
|
||||
goto error;
|
||||
vo->config = m_config_from_obj_desc_and_args(vo, vo->log, global, &desc,
|
||||
name, vo->opts->vo_defs, args);
|
||||
if (!vo->config)
|
||||
vo->priv = m_config_group_from_desc(vo, vo->log, global, &desc, name);
|
||||
if (!vo->priv)
|
||||
goto error;
|
||||
vo->priv = vo->config->optstruct;
|
||||
|
||||
if (pthread_create(&vo->in->thread, NULL, vo_thread, vo))
|
||||
goto error;
|
||||
@ -283,8 +282,7 @@ struct vo *init_best_video_out(struct mpv_global *global, struct vo_extra *ex)
|
||||
if (strlen(vo_list[n].name) == 0)
|
||||
goto autoprobe;
|
||||
bool p = !!vo_list[n + 1].name;
|
||||
struct vo *vo = vo_create(p, global, ex, vo_list[n].name,
|
||||
vo_list[n].attribs);
|
||||
struct vo *vo = vo_create(p, global, ex, vo_list[n].name);
|
||||
if (vo)
|
||||
return vo;
|
||||
}
|
||||
@ -296,7 +294,7 @@ autoprobe:
|
||||
const struct vo_driver *driver = video_out_drivers[i];
|
||||
if (driver == &video_out_null)
|
||||
break;
|
||||
struct vo *vo = vo_create(true, global, ex, (char *)driver->name, NULL);
|
||||
struct vo *vo = vo_create(true, global, ex, (char *)driver->name);
|
||||
if (vo)
|
||||
return vo;
|
||||
}
|
||||
|
@ -312,17 +312,16 @@ struct vo_driver {
|
||||
const void *priv_defaults;
|
||||
|
||||
// List of options to parse into priv struct (requires priv_size to be set)
|
||||
// Deprecated. Use global options or global_opts instead.
|
||||
// This will register them as global options (with options_prefix), and
|
||||
// copy the current value at VO creation time to the priv struct.
|
||||
const struct m_option *options;
|
||||
|
||||
// Global options to register if the VO is compiled in.
|
||||
// mp_get_config_group() or other function can be used to access them.
|
||||
const struct m_sub_options *global_opts;
|
||||
// All options in the above array are prefixed with this string. (It's just
|
||||
// for convenience and makes no difference in semantics.)
|
||||
const char *options_prefix;
|
||||
|
||||
// Evil hack: add .options as global options, using the provided prefix.
|
||||
// For further evilness, the options will be copied to the priv struct
|
||||
// like with normal .options behavior.
|
||||
const char *legacy_prefix;
|
||||
// Registers global options that go to a separate options struct.
|
||||
const struct m_sub_options *global_opts;
|
||||
};
|
||||
|
||||
struct vo {
|
||||
@ -356,7 +355,6 @@ struct vo {
|
||||
|
||||
struct m_config_cache *opts_cache; // cache for ->opts
|
||||
struct mp_vo_opts *opts;
|
||||
struct m_config *config; // config for ->priv
|
||||
|
||||
bool want_redraw; // redraw as soon as possible
|
||||
|
||||
|
@ -1747,5 +1747,5 @@ const struct vo_driver video_out_direct3d = {
|
||||
.priv_size = sizeof(d3d_priv),
|
||||
.priv_defaults = &defaults,
|
||||
.options = opts,
|
||||
.legacy_prefix = "vo-direct3d",
|
||||
.options_prefix = "vo-direct3d",
|
||||
};
|
||||
|
@ -490,5 +490,4 @@ const struct vo_driver video_out_drm = {
|
||||
.wait_events = wait_events,
|
||||
.wakeup = wakeup,
|
||||
.priv_size = sizeof(struct priv),
|
||||
.legacy_prefix = "drm",
|
||||
};
|
||||
|
@ -160,18 +160,6 @@ const struct vo_driver video_out_image =
|
||||
.name = "image",
|
||||
.untimed = true,
|
||||
.priv_size = sizeof(struct priv),
|
||||
.options = (const struct m_option[]) {
|
||||
OPT_SUBOPT_LEGACY("jpeg-quality", "vo-image-jpeg-quality"),
|
||||
OPT_SUBOPT_LEGACY("jpeg-smooth", "vo-image-jpeg-smooth"),
|
||||
OPT_SUBOPT_LEGACY("jpeg-source-chroma", "vo-image-jpeg-source-chroma"),
|
||||
OPT_SUBOPT_LEGACY("png-compression", "vo-image-png-compression"),
|
||||
OPT_SUBOPT_LEGACY("png-filter", "vo-image-png-filter"),
|
||||
OPT_SUBOPT_LEGACY("format", "vo-image-format"),
|
||||
OPT_SUBOPT_LEGACY("high-bit-depth", "vo-image-high-bit-depth"),
|
||||
OPT_SUBOPT_LEGACY("tag-colorspace", "vo-image-tag-colorspace"),
|
||||
OPT_SUBOPT_LEGACY("outdir", "vo-image-outdir"),
|
||||
{0},
|
||||
},
|
||||
.preinit = preinit,
|
||||
.query_format = query_format,
|
||||
.reconfig = reconfig,
|
||||
|
@ -101,5 +101,5 @@ const struct vo_driver video_out_null = {
|
||||
OPT_DOUBLE("fps", cfg_fps, M_OPT_RANGE, .min = 0, .max = 10000),
|
||||
{0},
|
||||
},
|
||||
.legacy_prefix = "vo-null",
|
||||
.options_prefix = "vo-null",
|
||||
};
|
||||
|
@ -62,40 +62,13 @@ struct vo_opengl_opts {
|
||||
int pattern[2];
|
||||
};
|
||||
|
||||
#define OPT_BASE_STRUCT struct vo_opengl_opts
|
||||
static const struct m_sub_options vo_opengl_conf = {
|
||||
.opts = (const m_option_t[]) {
|
||||
OPT_FLAG("opengl-glfinish", use_glFinish, 0),
|
||||
OPT_FLAG("opengl-waitvsync", waitvsync, 0),
|
||||
OPT_INT("opengl-swapinterval", swap_interval, 0),
|
||||
OPT_CHOICE("opengl-dwmflush", dwm_flush, 0,
|
||||
({"no", -1}, {"auto", 0}, {"windowed", 1}, {"yes", 2})),
|
||||
OPT_FLAG("opengl-dcomposition", allow_direct_composition, 0),
|
||||
OPT_FLAG("opengl-debug", use_gl_debug, 0),
|
||||
OPT_STRING_VALIDATE("opengl-backend", backend, 0,
|
||||
mpgl_validate_backend_opt),
|
||||
OPT_FLAG("opengl-sw", allow_sw, 0),
|
||||
OPT_CHOICE("opengl-es", es, 0, ({"no", -1}, {"auto", 0}, {"yes", 1})),
|
||||
OPT_INTPAIR("opengl-check-pattern", pattern, 0),
|
||||
OPT_INTRANGE("opengl-vsync-fences", vsync_fences, 0,
|
||||
0, NUM_VSYNC_FENCES),
|
||||
|
||||
{0}
|
||||
},
|
||||
.defaults = &(const struct vo_opengl_opts){
|
||||
.swap_interval = 1,
|
||||
.allow_direct_composition = 1,
|
||||
},
|
||||
.size = sizeof(struct vo_opengl_opts),
|
||||
};
|
||||
|
||||
struct gl_priv {
|
||||
struct vo *vo;
|
||||
struct mp_log *log;
|
||||
MPGLContext *glctx;
|
||||
GL *gl;
|
||||
|
||||
struct vo_opengl_opts *opts;
|
||||
struct vo_opengl_opts opts;
|
||||
|
||||
struct gl_video *renderer;
|
||||
|
||||
@ -133,7 +106,7 @@ static void resize(struct gl_priv *p)
|
||||
static void check_pattern(struct vo *vo, int item)
|
||||
{
|
||||
struct gl_priv *p = vo->priv;
|
||||
int expected = p->opts->pattern[p->last_pattern];
|
||||
int expected = p->opts.pattern[p->last_pattern];
|
||||
if (item == expected) {
|
||||
p->last_pattern++;
|
||||
if (p->last_pattern >= 2)
|
||||
@ -151,7 +124,7 @@ static void draw_frame(struct vo *vo, struct vo_frame *frame)
|
||||
struct gl_priv *p = vo->priv;
|
||||
GL *gl = p->gl;
|
||||
|
||||
if (gl->FenceSync && p->num_vsync_fences < p->opts->vsync_fences) {
|
||||
if (gl->FenceSync && p->num_vsync_fences < p->opts.vsync_fences) {
|
||||
GLsync fence = gl->FenceSync(GL_SYNC_GPU_COMMANDS_COMPLETE, 0);;
|
||||
if (fence)
|
||||
p->vsync_fences[p->num_vsync_fences++] = fence;
|
||||
@ -159,7 +132,7 @@ static void draw_frame(struct vo *vo, struct vo_frame *frame)
|
||||
|
||||
gl_video_render_frame(p->renderer, frame, gl->main_fb);
|
||||
|
||||
if (p->opts->use_glFinish)
|
||||
if (p->opts.use_glFinish)
|
||||
gl->Finish();
|
||||
}
|
||||
|
||||
@ -171,30 +144,30 @@ static void flip_page(struct vo *vo)
|
||||
mpgl_swap_buffers(p->glctx);
|
||||
|
||||
p->frames_rendered++;
|
||||
if (p->frames_rendered > 5 && !p->opts->use_gl_debug)
|
||||
if (p->frames_rendered > 5 && !p->opts.use_gl_debug)
|
||||
gl_video_set_debug(p->renderer, false);
|
||||
|
||||
if (p->opts->use_glFinish)
|
||||
if (p->opts.use_glFinish)
|
||||
gl->Finish();
|
||||
|
||||
if (p->opts->waitvsync || p->opts->pattern[0]) {
|
||||
if (p->opts.waitvsync || p->opts.pattern[0]) {
|
||||
if (gl->GetVideoSync) {
|
||||
unsigned int n1 = 0, n2 = 0;
|
||||
gl->GetVideoSync(&n1);
|
||||
if (p->opts->waitvsync)
|
||||
if (p->opts.waitvsync)
|
||||
gl->WaitVideoSync(2, (n1 + 1) % 2, &n2);
|
||||
int step = n1 - p->prev_sgi_sync_count;
|
||||
p->prev_sgi_sync_count = n1;
|
||||
MP_DBG(vo, "Flip counts: %u->%u, step=%d\n", n1, n2, step);
|
||||
if (p->opts->pattern[0])
|
||||
if (p->opts.pattern[0])
|
||||
check_pattern(vo, step);
|
||||
} else {
|
||||
MP_WARN(vo, "GLX_SGI_video_sync not available, disabling.\n");
|
||||
p->opts->waitvsync = 0;
|
||||
p->opts->pattern[0] = 0;
|
||||
p->opts.waitvsync = 0;
|
||||
p->opts.pattern[0] = 0;
|
||||
}
|
||||
}
|
||||
while (p->opts->vsync_fences > 0 && p->num_vsync_fences >= p->opts->vsync_fences) {
|
||||
while (p->opts.vsync_fences > 0 && p->num_vsync_fences >= p->opts.vsync_fences) {
|
||||
gl->ClientWaitSync(p->vsync_fences[0], GL_SYNC_FLUSH_COMMANDS_BIT, 1e9);
|
||||
gl->DeleteSync(p->vsync_fences[0]);
|
||||
MP_TARRAY_REMOVE_AT(p->vsync_fences, p->num_vsync_fences, 0);
|
||||
@ -389,7 +362,6 @@ static int preinit(struct vo *vo)
|
||||
struct gl_priv *p = vo->priv;
|
||||
p->vo = vo;
|
||||
p->log = vo->log;
|
||||
p->opts = mp_get_config_group(vo, vo->global, &vo_opengl_conf);
|
||||
|
||||
int vo_flags = 0;
|
||||
|
||||
@ -399,29 +371,29 @@ static int preinit(struct vo *vo)
|
||||
if (alpha_mode == 1)
|
||||
vo_flags |= VOFLAG_ALPHA;
|
||||
|
||||
if (p->opts->use_gl_debug)
|
||||
if (p->opts.use_gl_debug)
|
||||
vo_flags |= VOFLAG_GL_DEBUG;
|
||||
|
||||
if (p->opts->es == 1)
|
||||
if (p->opts.es == 1)
|
||||
vo_flags |= VOFLAG_GLES;
|
||||
if (p->opts->es == -1)
|
||||
if (p->opts.es == -1)
|
||||
vo_flags |= VOFLAG_NO_GLES;
|
||||
|
||||
if (p->opts->allow_sw)
|
||||
if (p->opts.allow_sw)
|
||||
vo_flags |= VOFLAG_SW;
|
||||
|
||||
if (p->opts->allow_direct_composition)
|
||||
if (p->opts.allow_direct_composition)
|
||||
vo_flags |= VOFLAG_ANGLE_DCOMP;
|
||||
|
||||
p->glctx = mpgl_init(vo, p->opts->backend, vo_flags);
|
||||
p->glctx = mpgl_init(vo, p->opts.backend, vo_flags);
|
||||
if (!p->glctx)
|
||||
goto err_out;
|
||||
p->gl = p->glctx->gl;
|
||||
|
||||
p->glctx->dwm_flush_opt = p->opts->dwm_flush;
|
||||
p->glctx->dwm_flush_opt = p->opts.dwm_flush;
|
||||
|
||||
if (p->gl->SwapInterval) {
|
||||
p->gl->SwapInterval(p->opts->swap_interval);
|
||||
p->gl->SwapInterval(p->opts.swap_interval);
|
||||
} else {
|
||||
MP_VERBOSE(vo, "swap_control extension missing.\n");
|
||||
}
|
||||
@ -454,21 +426,7 @@ err_out:
|
||||
return -1;
|
||||
}
|
||||
|
||||
static const struct m_option legacy_options[] = {
|
||||
OPT_SUBOPT_LEGACY("glfinish", "opengl-glfinish"),
|
||||
OPT_SUBOPT_LEGACY("waitvsync", "opengl-waitvsync"),
|
||||
OPT_SUBOPT_LEGACY("swapinterval", "opengl-swapinterval"),
|
||||
OPT_SUBOPT_LEGACY("dwmflush", "opengl-dwmflush"),
|
||||
OPT_SUBOPT_LEGACY("dcomposition", "opengl-dcomposition"),
|
||||
OPT_SUBOPT_LEGACY("debug", "opengl-debug"),
|
||||
OPT_SUBOPT_LEGACY("backend", "opengl-backend"),
|
||||
OPT_SUBOPT_LEGACY("sw", "opengl-sw"),
|
||||
OPT_SUBOPT_LEGACY("es", "opengl-es"),
|
||||
OPT_SUBOPT_LEGACY("check-pattern", "opengl-check-pattern"),
|
||||
OPT_SUBOPT_LEGACY("vsync-fences", "opengl-vsync-fences"),
|
||||
OPT_SUBSTRUCT_LEGACY("", gl_video_conf_legacy),
|
||||
{0},
|
||||
};
|
||||
#define OPT_BASE_STRUCT struct gl_priv
|
||||
|
||||
const struct vo_driver video_out_opengl = {
|
||||
.description = "Extended OpenGL Renderer",
|
||||
@ -484,6 +442,28 @@ const struct vo_driver video_out_opengl = {
|
||||
.wakeup = wakeup,
|
||||
.uninit = uninit,
|
||||
.priv_size = sizeof(struct gl_priv),
|
||||
.options = legacy_options,
|
||||
.global_opts = &vo_opengl_conf,
|
||||
.options = (const m_option_t[]) {
|
||||
OPT_FLAG("opengl-glfinish", opts.use_glFinish, 0),
|
||||
OPT_FLAG("opengl-waitvsync", opts.waitvsync, 0),
|
||||
OPT_INT("opengl-swapinterval", opts.swap_interval, 0),
|
||||
OPT_CHOICE("opengl-dwmflush", opts.dwm_flush, 0,
|
||||
({"no", -1}, {"auto", 0}, {"windowed", 1}, {"yes", 2})),
|
||||
OPT_FLAG("opengl-dcomposition", opts.allow_direct_composition, 0),
|
||||
OPT_FLAG("opengl-debug", opts.use_gl_debug, 0),
|
||||
OPT_STRING_VALIDATE("opengl-backend", opts.backend, 0,
|
||||
mpgl_validate_backend_opt),
|
||||
OPT_FLAG("opengl-sw", opts.allow_sw, 0),
|
||||
OPT_CHOICE("opengl-es", opts.es, 0, ({"no", -1}, {"auto", 0}, {"yes", 1})),
|
||||
OPT_INTPAIR("opengl-check-pattern", opts.pattern, 0),
|
||||
OPT_INTRANGE("opengl-vsync-fences", opts.vsync_fences, 0,
|
||||
0, NUM_VSYNC_FENCES),
|
||||
|
||||
{0}
|
||||
},
|
||||
.priv_defaults = &(const struct gl_priv){
|
||||
.opts = {
|
||||
.swap_interval = 1,
|
||||
.allow_direct_composition = 1,
|
||||
},
|
||||
},
|
||||
};
|
||||
|
@ -144,7 +144,7 @@ static void copy_vo_opts(struct vo *vo)
|
||||
// copy the struct with an assignment.
|
||||
// Just remove all the dynamic data to avoid confusion.
|
||||
struct mp_vo_opts opts = *vo->opts;
|
||||
opts.video_driver_list = opts.vo_defs = NULL;
|
||||
opts.video_driver_list = NULL;
|
||||
opts.winname = NULL;
|
||||
opts.sws_opts = NULL;
|
||||
p->ctx->vo_opts = opts;
|
||||
@ -529,13 +529,6 @@ static int preinit(struct vo *vo)
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define OPT_BASE_STRUCT struct vo_priv
|
||||
static const struct m_option options[] = {
|
||||
OPT_SUBOPT_LEGACY("debug", "opengl-debug"),
|
||||
OPT_SUBSTRUCT_LEGACY("", gl_video_conf_legacy),
|
||||
{0},
|
||||
};
|
||||
|
||||
const struct vo_driver video_out_opengl_cb = {
|
||||
.description = "OpenGL Callbacks for libmpv",
|
||||
.name = "opengl-cb",
|
||||
@ -548,5 +541,4 @@ const struct vo_driver video_out_opengl_cb = {
|
||||
.flip_page = flip_page,
|
||||
.uninit = uninit,
|
||||
.priv_size = sizeof(struct vo_priv),
|
||||
.options = options,
|
||||
};
|
||||
|
@ -933,5 +933,5 @@ const struct vo_driver video_out_rpi = {
|
||||
.uninit = uninit,
|
||||
.priv_size = sizeof(struct priv),
|
||||
.options = options,
|
||||
.legacy_prefix = "rpi",
|
||||
.options_prefix = "rpi",
|
||||
};
|
||||
|
@ -1032,5 +1032,5 @@ const struct vo_driver video_out_sdl = {
|
||||
.flip_page = flip_page,
|
||||
.wait_events = wait_events,
|
||||
.wakeup = wakeup,
|
||||
.legacy_prefix = "sdl",
|
||||
.options_prefix = "sdl",
|
||||
};
|
||||
|
@ -696,5 +696,5 @@ const struct vo_driver video_out_vaapi = {
|
||||
OPT_FLAG("scaled-osd", force_scaled_osd, 0),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "vo-vaapi",
|
||||
.options_prefix = "vo-vaapi",
|
||||
};
|
||||
|
@ -1164,5 +1164,5 @@ const struct vo_driver video_out_vdpau = {
|
||||
OPT_REPLACED("output_surfaces", "output-surfaces"),
|
||||
{NULL},
|
||||
},
|
||||
.legacy_prefix = "vo-vdpau",
|
||||
.options_prefix = "vo-vdpau",
|
||||
};
|
||||
|
@ -677,6 +677,6 @@ const struct vo_driver video_out_wayland = {
|
||||
OPT_FLAG("rgb565", use_rgb565, 0),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "vo-wayland",
|
||||
.options_prefix = "vo-wayland",
|
||||
};
|
||||
|
||||
|
@ -933,5 +933,5 @@ const struct vo_driver video_out_xv = {
|
||||
OPT_REMOVED("no-colorkey", "use ck-method=none instead"),
|
||||
{0}
|
||||
},
|
||||
.legacy_prefix = "xv",
|
||||
.options_prefix = "xv",
|
||||
};
|
||||
|
Loading…
Reference in New Issue
Block a user