resource-fork-types 0.1.1

Support for reading common resource fork types in rust
Documentation
use std::collections::HashMap;

use binrw::{BinRead, BinReaderExt};
use resource_fork::Resource;

use crate::common::LongArrayPlusOne;

#[derive(Resource, BinRead, Debug)]
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
#[resource(code = "BNDL")]
#[br(big)]
pub struct Bundle {
    pub owner: fourcc::FourCC,
    pub owner_id: u16,

    #[br(map(|a: BundleTypeEntries| a.into()))]
    pub types: HashMap<fourcc::FourCC, Vec<BundleTypeEntry>>,
}

struct BundleTypeEntries {
    entries: HashMap<fourcc::FourCC, Vec<BundleTypeEntry>>,
}

impl BinRead for BundleTypeEntries {
    type Args<'a> = ();

    fn read_options<R: std::io::Read + std::io::Seek>(
        reader: &mut R,
        _: binrw::Endian,
        _: Self::Args<'_>,
    ) -> binrw::BinResult<Self> {
        let last_type_idx: u16 = reader.read_be()?;
        let mut entries = HashMap::new();
        for _ in 0..=last_type_idx {
            let code: fourcc::FourCC = reader.read_be()?;

            let array: LongArrayPlusOne<BundleTypeEntry> = reader.read_be()?;
            entries.insert(code, array.items);
        }

        Ok(Self { entries })
    }
}

impl From<BundleTypeEntries> for HashMap<fourcc::FourCC, Vec<BundleTypeEntry>> {
    fn from(val: BundleTypeEntries) -> Self {
        val.entries
    }
}

#[derive(BinRead, Debug)]
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
pub struct BundleTypeEntry {
    pub local_id: u16,
    pub resource_id: u16,
}