// SPDX-License-Identifier: Apache-2.0
// Copyright (c) 2025-present, fjall-rs
// Copyright (c) 2026-present, Structured World Foundation

use crate::io::{LittleEndian, ReadBytesExt};

pub struct Reader<'a> {
    bytes: &'a [u8],
    step_size: usize,
}

impl<'a> Reader<'a> {
    pub(crate) fn new(bytes: &'a [u8], offset: u32, len: u32, step_size: u8) -> Self {
        let offset = offset as usize;
        let len = len as usize;
        let step_size = step_size as usize;
        let size = len * step_size;
        let end = offset + size;

        Self {
            #[expect(
                clippy::indexing_slicing,
                reason = "we consider the caller to be trustworthy"
            )]
            bytes: &bytes[offset..end],
            step_size,
        }
    }

    pub fn len(&self) -> usize {
        self.bytes.len() / self.step_size
    }

    pub(crate) fn get(&self, idx: usize) -> usize {
        let offset = idx * self.step_size;

        #[expect(
            clippy::indexing_slicing,
            reason = "we consider the caller to be trustworthy"
        )]
        let mut bytes = &self.bytes[offset..];

        if self.step_size == 2 {
            unwrap!(bytes.read_u16::<LittleEndian>()).into()
        } else {
            unwrap!(bytes.read_u32::<LittleEndian>()) as usize
        }
    }
}
