isobmff/boxes/post_decoder_requirements.rs
1use std::io;
2
3use scuffle_bytes_util::zero_copy::{Deserialize, DeserializeSeed, Serialize, ZeroCopyReader};
4use scuffle_bytes_util::{BytesCow, IoResultExt};
5
6use super::{OriginalFormatBox, SchemeInformationBox, SchemeTypeBox};
7use crate::{BoxHeader, FullBoxHeader, IsoBox, UnknownBox, Utf8String};
8
9/// Restricted scheme information box
10///
11/// ISO/IEC 14496-12 - 8.15.3
12#[derive(IsoBox, Debug, PartialEq, Eq)]
13#[iso_box(box_type = b"rinf", crate_path = crate)]
14pub struct RestrictedSchemeInfoBox<'a> {
15 /// The contained [`OriginalFormatBox`]. (mandatory)
16 #[iso_box(nested_box)]
17 pub original_format: OriginalFormatBox,
18 /// The contained [`SchemeTypeBox`]. (mandatory)
19 #[iso_box(nested_box)]
20 pub scheme_type: SchemeTypeBox,
21 /// The contained [`SchemeInformationBox`]. (optional)
22 #[iso_box(nested_box(collect))]
23 pub info: Option<SchemeInformationBox<'a>>,
24 /// The contained [`CompatibleSchemeTypeBox`]es. (any quantity)
25 #[iso_box(nested_box(collect))]
26 pub csch: Vec<CompatibleSchemeTypeBox>,
27}
28
29/// Stereo video box
30///
31/// ISO/IEC 14496-12 - 8.15.4.2
32#[derive(IsoBox, Debug, PartialEq, Eq)]
33#[iso_box(box_type = b"stvi", skip_impl(deserialize_seed), crate_path = crate)]
34pub struct StereoVideoBox<'a> {
35 /// The full box header.
36 pub full_header: FullBoxHeader,
37 /// An integer. A zero value indicates that the content may only be displayed on
38 /// stereoscopic displays. When (`single_view_allowed` & 1) is equal to 1, it is allowed to display the
39 /// right view on a monoscopic single-view display. When (`single_view_allowed` & 2) is equal to 2, it is
40 /// allowed to display the left view on a monoscopic single-view display.
41 pub single_view_allowed: u8,
42 /// An integer that indicates the stereo arrangement scheme used and the stereo
43 /// indication type according to the used scheme.
44 /// The following values for `stereo_scheme` are specified:
45 ///
46 /// - `1`: The frame packing scheme as specified by the Frame packing arrangement Supplemental
47 /// Enhancement Information message of ISO/IEC 14496-10:2014.
48 /// - `2`: The stereo scheme as specified in ISO/IEC 23000-11 for both frame/service compatible and
49 /// 2D/3D mixed services.
50 /// - `3`: The arrangement type scheme as specified in ISO/IEC 13818-2:2013, Annex D
51 /// a value of `VideoFramePackingType` as defined in ISO/IEC 23091-2.
52 ///
53 /// Other values of stereo_scheme are reserved.
54 pub stereo_scheme: u32,
55 /// Indicates the number of bytes for the `stereo_indication_type` field.
56 pub length: u32,
57 /// Indicates the stereo arrangement type according to the used stereo indication
58 /// scheme. The syntax and semantics of `stereo_indication_type` depend on the value of `stereo_scheme`.
59 /// The syntax and semantics for stereo_indication_type for the following values of stereo_
60 /// scheme are specified as follows:
61 ///
62 /// - `stereo_scheme` equal to 1: The value of length shall be 4 and `stereo_indication_type` shall
63 /// be `unsigned int(32)` which contains the `frame_packing_arrangement_type` value from
64 /// ISO/IEC 14496-10:2014, Table D.8 ('Definition of frame_packing_arrangement_type').
65 /// - `stereo_scheme` equal to 2: The value of length shall be 4 and `stereo_indication_type` shall be
66 /// `unsigned int(32)` which contains the type value from ISO/IEC 13818-2:2013, Table D.1
67 /// ('Definition of arrangement_type').
68 /// - `stereo_scheme` equal to 3: The value of length shall be 2 and `stereo_indication_type` shall
69 /// contain two syntax elements of `unsigned int(8)`. The first syntax element shall contain the
70 /// stereoscopic composition type from ISO/IEC 23000-11:2009, Table 4. The least significant
71 /// bit of the second syntax element shall contain the value of `is_left_first` as specified in
72 /// ISO/IEC 23000-11:2009, subclause 8.4.3, while the other bits are reserved and shall be set
73 /// to 0.
74 /// - `stereo_scheme` equal to 4: The value of length shall be 2 and `stereo_indication_type` shall
75 /// contain two syntax elements of `unsigned int(8)`. The first syntax element shall contain a
76 /// `VideoFramePackingType` from ISO/IEC 23091-2. The least significant bit of the second syntax
77 /// element shall contain the value of `QuincunxSamplingFlag` as specified in ISO/IEC 23091-2,
78 /// while the other bits are reserved and shall be set to 0. `PackedContentInterpretationType`
79 /// specified in ISO/IEC 23091-2 is inferred to be equal to 1.
80 /// - `stereo_scheme` equal to 5: The value of length shall be 3 and `stereo_indication_type` shall contain
81 /// three syntax elements of type `unsigned int(8)`. The first syntax element shall contain a
82 /// `VideoFramePackingType` from ISO/IEC 23091-2. The least significant bit of the second syntax
83 /// element shall contain the value of `QuincunxSamplingFlag` as specified in ISO/IEC 23091-2,
84 /// while the other bits are reserved and shall be set to 0. The third syntax element shall contain
85 /// the `PackedContentInterpretationType` from ISO/IEC 23091-2.
86 pub stereo_indication_type: BytesCow<'a>,
87 /// Any other contained boxes.
88 #[iso_box(nested_box(collect_unknown))]
89 pub any_box: Vec<UnknownBox<'a>>,
90}
91
92impl<'a> DeserializeSeed<'a, BoxHeader> for StereoVideoBox<'a> {
93 fn deserialize_seed<R>(mut reader: R, _seed: BoxHeader) -> io::Result<Self>
94 where
95 R: ZeroCopyReader<'a>,
96 {
97 let full_header = FullBoxHeader::deserialize(&mut reader)?;
98
99 let single_view_allowed = u32::deserialize(&mut reader)?;
100 let single_view_allowed = (single_view_allowed & 0b11) as u8;
101 let stereo_scheme = u32::deserialize(&mut reader)?;
102
103 let length = u32::deserialize(&mut reader)?;
104 let stereo_indication_type = reader.try_read(length as usize)?;
105
106 let mut any_box = Vec::new();
107 loop {
108 let Some(box_header) = BoxHeader::deserialize(&mut reader).eof_to_none()? else {
109 break;
110 };
111 let Some(unknown_box) = UnknownBox::deserialize_seed(&mut reader, box_header).eof_to_none()? else {
112 break;
113 };
114 any_box.push(unknown_box);
115 }
116
117 Ok(Self {
118 full_header,
119 single_view_allowed,
120 stereo_scheme,
121 length,
122 stereo_indication_type,
123 any_box,
124 })
125 }
126}
127
128/// Compatible scheme type box
129///
130/// ISO/IEC 14496-12 - 8.15.5
131#[derive(IsoBox, Debug, PartialEq, Eq)]
132#[iso_box(box_type = b"csch", skip_impl(deserialize_seed, serialize), crate_path = crate)]
133pub struct CompatibleSchemeTypeBox {
134 /// The full box header.
135 pub full_header: FullBoxHeader,
136 /// The code defining the protection or restriction scheme, normally expressed as a four character code.
137 pub scheme_type: [u8; 4],
138 /// The version of the scheme (used to create the content).
139 pub scheme_version: u32,
140 /// An absolute URI allowing for the option of directing the user to a web-page if they do not
141 /// have the scheme installed on their system.
142 pub scheme_uri: Option<Utf8String>,
143}
144
145impl<'a> DeserializeSeed<'a, BoxHeader> for CompatibleSchemeTypeBox {
146 fn deserialize_seed<R>(mut reader: R, _seed: BoxHeader) -> io::Result<Self>
147 where
148 R: ZeroCopyReader<'a>,
149 {
150 let full_header = FullBoxHeader::deserialize(&mut reader)?;
151
152 let scheme_type = <[u8; 4]>::deserialize(&mut reader)?;
153 let scheme_version = u32::deserialize(&mut reader)?;
154 let scheme_uri = if (*full_header.flags & 0x000001) != 0 {
155 Some(Utf8String::deserialize(&mut reader)?)
156 } else {
157 None
158 };
159
160 Ok(Self {
161 full_header,
162 scheme_type,
163 scheme_version,
164 scheme_uri,
165 })
166 }
167}
168
169impl Serialize for CompatibleSchemeTypeBox {
170 fn serialize<W>(&self, mut writer: W) -> io::Result<()>
171 where
172 W: std::io::Write,
173 {
174 self.serialize_box_header(&mut writer)?;
175 self.full_header.serialize(&mut writer)?;
176
177 self.scheme_type.serialize(&mut writer)?;
178 self.scheme_version.serialize(&mut writer)?;
179
180 if (*self.full_header.flags & 0x000001) != 0 {
181 self.scheme_uri
182 .as_ref()
183 .ok_or(io::Error::new(io::ErrorKind::InvalidData, "scheme_uri is required"))?
184 .serialize(&mut writer)?;
185 }
186
187 Ok(())
188 }
189}