diff --git a/audio/out/ao_coreaudio_utils.c b/audio/out/ao_coreaudio_utils.c index 21ffbf0dc8..79189380ab 100644 --- a/audio/out/ao_coreaudio_utils.c +++ b/audio/out/ao_coreaudio_utils.c @@ -268,6 +268,40 @@ void ca_print_asbd(struct ao *ao, const char *description, talloc_free(format); } +// Return whether new is an improvement over old (req is the requested format). +bool ca_asbd_is_better(AudioStreamBasicDescription *req, + AudioStreamBasicDescription *old, + AudioStreamBasicDescription *new) +{ + if (req->mFormatID != new->mFormatID) + return false; + + int mpfmt_req = ca_asbd_to_mp_format(old); + int mpfmt_new = ca_asbd_to_mp_format(new); + if (!mpfmt_new) + return false; + + if (mpfmt_req != mpfmt_new) { + int mpfmt_old = ca_asbd_to_mp_format(old); + if (af_format_conversion_score(mpfmt_req, mpfmt_old) > + af_format_conversion_score(mpfmt_req, mpfmt_new)) + return false; + } + + if (req->mSampleRate != new->mSampleRate) { + if (old->mSampleRate > new->mSampleRate) + return false; + } + + if (req->mChannelsPerFrame != new->mChannelsPerFrame) { + if (old->mChannelsPerFrame > new->mChannelsPerFrame || + new->mChannelsPerFrame > MP_NUM_CHANNELS) + return false; + } + + return true; +} + int64_t ca_frames_to_us(struct ao *ao, uint32_t frames) { return frames / (float) ao->samplerate * 1e6; diff --git a/audio/out/ao_coreaudio_utils.h b/audio/out/ao_coreaudio_utils.h index b5f8e7f2ba..2e87cb472d 100644 --- a/audio/out/ao_coreaudio_utils.h +++ b/audio/out/ao_coreaudio_utils.h @@ -58,6 +58,9 @@ void ca_print_asbd(struct ao *ao, const char *description, bool ca_asbd_equals(const AudioStreamBasicDescription *a, const AudioStreamBasicDescription *b); int ca_asbd_to_mp_format(const AudioStreamBasicDescription *asbd); +bool ca_asbd_is_better(AudioStreamBasicDescription *req, + AudioStreamBasicDescription *old, + AudioStreamBasicDescription *new); int64_t ca_frames_to_us(struct ao *ao, uint32_t frames); int64_t ca_get_latency(const AudioTimeStamp *ts);