diff options
author | Rodeo <[email protected]> | 2013-02-05 17:53:03 +0000 |
---|---|---|
committer | Rodeo <[email protected]> | 2013-02-05 17:53:03 +0000 |
commit | 5ca5ec3e6f4ebb47e92984a4ef859510df56b537 (patch) | |
tree | 22dbb88491ce5e6d7b8c844ebdb79581993f2e52 /libhb/common.c | |
parent | 4017dfc2050336c4476f89fd4c4e358449b9376e (diff) |
Audio dithering.
Works with encoders that accept 16-bit signed integers as input (currently, only ffflac).
When supported, the default method is standard triangular.
CLI users can request a specific dither algorithm via the --adither option.
git-svn-id: svn://svn.handbrake.fr/HandBrake/trunk@5241 b64f7644-9d1e-0410-96f1-a4d463321fa5
Diffstat (limited to 'libhb/common.c')
-rw-r--r-- | libhb/common.c | 57 |
1 files changed, 57 insertions, 0 deletions
diff --git a/libhb/common.c b/libhb/common.c index 355b458e5..cfbeb6185 100644 --- a/libhb/common.c +++ b/libhb/common.c @@ -83,6 +83,17 @@ int hb_audio_bitrates_count = sizeof(hb_audio_bitrates) / sizeof(hb_rate_t); static hb_error_handler_t *error_handler = NULL; +hb_dither_t hb_audio_dithers[] = +{ + { "default", "auto", AV_RESAMPLE_DITHER_NONE - 1, }, + { "none", "none", AV_RESAMPLE_DITHER_NONE, }, + { "rectangular", "rectangular", AV_RESAMPLE_DITHER_RECTANGULAR, }, + { "triangular", "triangular", AV_RESAMPLE_DITHER_TRIANGULAR, }, + { "triangular with high pass", "triangular_hp", AV_RESAMPLE_DITHER_TRIANGULAR_HP, }, + { "triangular with noise shaping", "triangular_ns", AV_RESAMPLE_DITHER_TRIANGULAR_NS, }, +}; +int hb_audio_dithers_count = sizeof(hb_audio_dithers) / sizeof(hb_dither_t); + hb_mixdown_t hb_audio_mixdowns[] = { { "None", "HB_AMIXDOWN_NONE", "none", HB_AMIXDOWN_NONE }, @@ -138,6 +149,8 @@ hb_rate_t* hb_get_audio_rates() { return hb_audio_rates; } int hb_get_audio_rates_count() { return hb_audio_rates_count; } hb_rate_t* hb_get_audio_bitrates() { return hb_audio_bitrates; } int hb_get_audio_bitrates_count() { return hb_audio_bitrates_count; } +hb_dither_t* hb_get_audio_dithers() { return hb_audio_dithers; } +int hb_get_audio_dithers_count() { return hb_audio_dithers_count; } hb_mixdown_t* hb_get_audio_mixdowns() { return hb_audio_mixdowns; } int hb_get_audio_mixdowns_count() { return hb_audio_mixdowns_count; } hb_encoder_t* hb_get_video_encoders() { return hb_video_encoders; } @@ -145,6 +158,47 @@ int hb_get_video_encoders_count() { return hb_video_encoders_count; } hb_encoder_t* hb_get_audio_encoders() { return hb_audio_encoders; } int hb_get_audio_encoders_count() { return hb_audio_encoders_count; } +int hb_audio_dither_get_default() +{ + // "auto" + return hb_audio_dithers[0].method; +} + +int hb_audio_dither_get_default_method() +{ + /* + * input could be s16 (possibly already dithered) converted to flt, so + * let's use a "low-risk" dither algorithm (standard triangular). + */ + return AV_RESAMPLE_DITHER_TRIANGULAR; +} + +int hb_audio_dither_is_supported(uint32_t codec) +{ + // encoder's input sample format must be s16(p) + switch (codec) + { + case HB_ACODEC_FFFLAC: + return 1; + default: + return 0; + } +} + +const char* hb_audio_dither_get_description(int method) +{ + int i; + for (i = 0; i < hb_audio_dithers_count; i++) + { + if (hb_audio_dithers[i].method == method) + { + return hb_audio_dithers[i].description; + } + } + return ""; +} + + int hb_mixdown_is_supported(int mixdown, uint32_t codec, uint64_t layout) { return (hb_mixdown_has_codec_support(mixdown, codec) && @@ -2240,6 +2294,7 @@ void hb_audio_config_init(hb_audio_config_t * audiocfg) audiocfg->out.dynamic_range_compression = 0; audiocfg->out.gain = 0; audiocfg->out.normalize_mix_level = 0; + audiocfg->out.dither_method = hb_audio_dither_get_default(); audiocfg->out.name = NULL; } @@ -2290,6 +2345,7 @@ int hb_audio_add(const hb_job_t * job, const hb_audio_config_t * audiocfg) audio->config.out.normalize_mix_level = 0; audio->config.out.compression_level = -1; audio->config.out.quality = HB_INVALID_AUDIO_QUALITY; + audio->config.out.dither_method = AV_RESAMPLE_DITHER_NONE; } else { @@ -2303,6 +2359,7 @@ int hb_audio_add(const hb_job_t * job, const hb_audio_config_t * audiocfg) audio->config.out.mixdown = audiocfg->out.mixdown; audio->config.out.gain = audiocfg->out.gain; audio->config.out.normalize_mix_level = audiocfg->out.normalize_mix_level; + audio->config.out.dither_method = audiocfg->out.dither_method; } if (audiocfg->out.name && *audiocfg->out.name) { |