Skip to main content

hang/catalog/video/
codec.rs

1use super::*;
2
3use std::str::FromStr;
4
5use derive_more::{Display, From};
6
7use crate::Error;
8
9/// Supported video codec mimetypes.
10// TODO implement serde for convience
11#[derive(Debug, Clone, PartialEq, Eq, Display, From)]
12#[non_exhaustive]
13pub enum VideoCodec {
14	/// H.264/AVC codec with profile and level information
15	H264(H264),
16	/// H.265/HEVC codec with profile and level information
17	H265(H265),
18	/// VP9 codec with profile and color information
19	VP9(VP9),
20	/// AV1 codec with profile and level information
21	AV1(AV1),
22
23	/// VP8 codec (no additional parameters)
24	#[display("vp8")]
25	VP8,
26
27	/// Unknown or unsupported codec with original string
28	#[display("{_0}")]
29	Unknown(String),
30}
31
32impl FromStr for VideoCodec {
33	type Err = Error;
34
35	fn from_str(s: &str) -> Result<Self, Self::Err> {
36		if s.starts_with("avc1.") || s.starts_with("avc3.") {
37			return H264::from_str(s).map(Into::into);
38		} else if s.starts_with("hvc1.") || s.starts_with("hev1.") {
39			return H265::from_str(s).map(Into::into);
40		} else if s == "vp8" {
41			return Ok(Self::VP8);
42		} else if s.starts_with("vp09.") {
43			return VP9::from_str(s).map(Into::into);
44		} else if s.starts_with("av01.") {
45			return AV1::from_str(s).map(Into::into);
46		}
47
48		Ok(Self::Unknown(s.to_string()))
49	}
50}
51
52#[cfg(test)]
53mod test {
54	use super::*;
55
56	#[test]
57	fn test_vp8() {
58		let encoded = "vp8";
59		let decoded = VideoCodec::from_str(encoded).expect("failed to parse");
60		assert_eq!(decoded, VideoCodec::VP8);
61
62		let output = decoded.to_string();
63		assert_eq!(output, encoded);
64	}
65}