diff options
author | Michael Niedermayer <michaelni@gmx.at> | 2012-11-25 20:10:09 +0400 |
---|---|---|
committer | Michael Niedermayer <michaelni@gmx.at> | 2012-12-08 04:34:28 +0400 |
commit | a8e0d51bb8141bbe64d4e22aec72742199208192 (patch) | |
tree | c595a019f9cd97d7b978b86cf18bc19649be26f6 /libavutil/opt.c | |
parent | 419ade4b6193c6eb626cda01b21e7091f42b2cc2 (diff) |
opt: Add support to query ranges
Reviewed-by: Stefano Sabatini <stefasab@gmail.com>
Signed-off-by: Michael Niedermayer <michaelni@gmx.at>
Diffstat (limited to 'libavutil/opt.c')
-rw-r--r-- | libavutil/opt.c | 80 |
1 files changed, 80 insertions, 0 deletions
diff --git a/libavutil/opt.c b/libavutil/opt.c index dfee6d24b8..f060bd1a48 100644 --- a/libavutil/opt.c +++ b/libavutil/opt.c @@ -1166,6 +1166,86 @@ void *av_opt_ptr(const AVClass *class, void *obj, const char *name) return (uint8_t*)obj + opt->offset; } +int av_opt_query_ranges(AVOptionRanges **ranges_arg, void *obj, const char *key, int flags) { + const AVClass *c = *(AVClass**)obj; + int (*callback)(AVOptionRanges **, void *obj, const char *key, int flags) = NULL; + + if(c->version > (52 << 16 | 11 << 8)) + callback = c->query_ranges; + + if(!callback) + callback = av_opt_query_ranges_default; + + return callback(ranges_arg, obj, key, flags); +} + +int av_opt_query_ranges_default(AVOptionRanges **ranges_arg, void *obj, const char *key, int flags) { + AVOptionRanges *ranges = av_mallocz(sizeof(*ranges)); + AVOptionRange **range_array = av_mallocz(sizeof(void*)); + AVOptionRange *range = av_mallocz(sizeof(*range)); + const AVOption *field = av_opt_find(obj, key, NULL, 0, flags); + + *ranges_arg = NULL; + + if(!ranges || !range || !range_array || !field) + goto fail; + + ranges->range = range_array; + ranges->range[0] = range; + ranges->nb_ranges = 1; + range->is_range = 1; + range->value_min = field->min; + range->value_max = field->max; + + switch(field->type){ + case AV_OPT_TYPE_INT: + case AV_OPT_TYPE_INT64: + case AV_OPT_TYPE_PIXEL_FMT: + case AV_OPT_TYPE_SAMPLE_FMT: + case AV_OPT_TYPE_FLOAT: + case AV_OPT_TYPE_DOUBLE: + break; + case AV_OPT_TYPE_STRING: + range->component_min = 0; + range->component_max = 0x10FFFF; // max unicode value + range->value_min = -1; + range->value_max = INT_MAX; + break; + case AV_OPT_TYPE_RATIONAL: + range->component_min = INT_MIN; + range->component_max = INT_MAX; + break; + case AV_OPT_TYPE_IMAGE_SIZE: + range->component_min = 0; + range->component_max = INT_MAX/128/8; + range->value_min = 0; + range->value_max = INT_MAX/8; + break; + default: + goto fail; + } + + *ranges_arg = ranges; + return 0; +fail: + av_free(ranges); + av_free(range); + return -1; +} + +void av_opt_freep_ranges(AVOptionRanges **rangesp) { + int i; + AVOptionRanges *ranges = *rangesp; + + for(i=0; i<ranges->nb_ranges; i++){ + AVOptionRange *range = ranges->range[i]; + av_freep(&range->str); + av_freep(&ranges->range[i]); + } + av_freep(&ranges->range); + av_freep(rangesp); +} + #ifdef TEST typedef struct TestContext |