use crate::{
codec_id::{AudioCodecId, VideoCodecId},
error::{AudioDecodeError, VideoDecodeError},
};
pub fn for_video(
codec: VideoCodecId,
_extradata: Option<&[u8]>,
) -> Result<String, VideoDecodeError> {
match codec {
VideoCodecId::Vp8 => Ok("vp8".into()),
VideoCodecId::H264 | VideoCodecId::Hevc | VideoCodecId::Vp9 | VideoCodecId::Av1 => {
Err(VideoDecodeError::UnsupportedCodec(format!(
"{codec:?} requires extradata parsing; use open_with_codec_string"
)))
}
}
}
pub fn for_audio(
codec: AudioCodecId,
audio_specific_config: Option<&[u8]>,
) -> Result<String, AudioDecodeError> {
match codec {
AudioCodecId::Opus => Ok("opus".into()),
AudioCodecId::PcmS16 => Ok("pcm-s16".into()),
AudioCodecId::Flac => Ok("flac".into()),
AudioCodecId::Vorbis => Ok("vorbis".into()),
AudioCodecId::Ulaw => Ok("ulaw".into()),
AudioCodecId::Alaw => Ok("alaw".into()),
AudioCodecId::Aac => {
let aot = audio_specific_config
.and_then(|b| b.first().copied())
.map(|b| b >> 3)
.unwrap_or(2);
Ok(format!("mp4a.40.{aot}"))
}
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn fixed_video_strings() {
assert_eq!(for_video(VideoCodecId::Vp8, None).unwrap(), "vp8");
}
#[test]
fn extradata_required_codecs_error() {
assert!(matches!(
for_video(VideoCodecId::H264, None),
Err(VideoDecodeError::UnsupportedCodec(_))
));
}
#[test]
fn fixed_audio_strings() {
assert_eq!(for_audio(AudioCodecId::Opus, None).unwrap(), "opus");
assert_eq!(for_audio(AudioCodecId::Flac, None).unwrap(), "flac");
}
#[test]
fn aac_default_is_lc() {
assert_eq!(for_audio(AudioCodecId::Aac, None).unwrap(), "mp4a.40.2");
}
#[test]
fn aac_aot_extracted_from_config() {
let cfg = [0b0010_1000_u8];
assert_eq!(
for_audio(AudioCodecId::Aac, Some(&cfg)).unwrap(),
"mp4a.40.5"
);
}
}