re_mp4/mp4box/
tfdt.rs

1use byteorder::{BigEndian, ReadBytesExt};
2use serde::Serialize;
3use std::io::{Read, Seek};
4
5use crate::mp4box::{
6    box_start, read_box_header_ext, skip_bytes_to, BoxType, Error, Mp4Box, ReadBox, Result,
7    HEADER_EXT_SIZE, HEADER_SIZE,
8};
9
10#[derive(Debug, Clone, PartialEq, Eq, Default, Serialize)]
11pub struct TfdtBox {
12    pub version: u8,
13    pub flags: u32,
14    pub base_media_decode_time: u64,
15}
16
17impl TfdtBox {
18    pub fn get_type(&self) -> BoxType {
19        BoxType::TfdtBox
20    }
21
22    pub fn get_size(&self) -> u64 {
23        let mut sum = HEADER_SIZE + HEADER_EXT_SIZE;
24        if self.version == 1 {
25            sum += 8;
26        } else {
27            sum += 4;
28        }
29        sum
30    }
31}
32
33impl Mp4Box for TfdtBox {
34    fn box_type(&self) -> BoxType {
35        self.get_type()
36    }
37
38    fn box_size(&self) -> u64 {
39        self.get_size()
40    }
41
42    fn to_json(&self) -> Result<String> {
43        Ok(serde_json::to_string(&self).expect("Failed to convert to JSON"))
44    }
45
46    fn summary(&self) -> Result<String> {
47        let s = format!("base_media_decode_time={}", self.base_media_decode_time);
48        Ok(s)
49    }
50}
51
52impl<R: Read + Seek> ReadBox<&mut R> for TfdtBox {
53    fn read_box(reader: &mut R, size: u64) -> Result<Self> {
54        let start = box_start(reader)?;
55
56        let (version, flags) = read_box_header_ext(reader)?;
57
58        let base_media_decode_time = if version == 1 {
59            reader.read_u64::<BigEndian>()?
60        } else if version == 0 {
61            reader.read_u32::<BigEndian>()? as u64
62        } else {
63            return Err(Error::InvalidData("version must be 0 or 1"));
64        };
65
66        skip_bytes_to(reader, start + size)?;
67
68        Ok(Self {
69            version,
70            flags,
71            base_media_decode_time,
72        })
73    }
74}