use alloc::borrow::Cow;
use alloc::vec::Vec;
use ownable::IntoOwned;
use serde::Deserialize;
use serde_json::Number;
use crate::buffer::BufferView;
use crate::{Extensions, Extras, Idx};
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum ComponentTypeEnum {
I8,
U8,
I16,
U16,
U32,
F32,
}
#[derive(Clone, Copy, PartialEq, Eq, Deserialize, IntoOwned)]
#[serde(transparent)]
pub struct ComponentType(pub u64);
impl core::fmt::Debug for ComponentType {
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
if let Some(e) = self.to_enum() {
e.fmt(f)
} else {
self.0.fmt(f)
}
}
}
impl ComponentType {
pub const I8: Self = Self(5120);
pub const U8: Self = Self(5121);
pub const I16: Self = Self(5122);
pub const U16: Self = Self(5123);
pub const U32: Self = Self(5125);
pub const F32: Self = Self(5126);
pub fn to_enum(self) -> Option<ComponentTypeEnum> {
Some(match self {
Self::I8 => ComponentTypeEnum::I8,
Self::U8 => ComponentTypeEnum::U8,
Self::I16 => ComponentTypeEnum::I16,
Self::U16 => ComponentTypeEnum::U16,
Self::U32 => ComponentTypeEnum::U32,
Self::F32 => ComponentTypeEnum::F32,
_ => return None,
})
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum ElementTypeEnum {
Scalar,
Vec2,
Vec3,
Vec4,
Mat2,
Mat3,
Mat4,
}
#[derive(Clone, PartialEq, Eq, Deserialize, IntoOwned)]
#[serde(transparent)]
pub struct ElementType<'a>(#[serde(borrow)] pub Cow<'a, str>);
impl core::fmt::Debug for ElementType<'_> {
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
if let Some(e) = self.to_enum() {
e.fmt(f)
} else {
self.0.fmt(f)
}
}
}
impl ElementType<'_> {
pub const SCALAR: Self = Self(Cow::Borrowed("SCALAR"));
pub const VEC2: Self = Self(Cow::Borrowed("VEC2"));
pub const VEC3: Self = Self(Cow::Borrowed("VEC3"));
pub const VEC4: Self = Self(Cow::Borrowed("VEC4"));
pub const MAT2: Self = Self(Cow::Borrowed("MAT2"));
pub const MAT3: Self = Self(Cow::Borrowed("MAT3"));
pub const MAT4: Self = Self(Cow::Borrowed("MAT4"));
pub fn to_enum(&self) -> Option<ElementTypeEnum> {
if *self == Self::SCALAR {
return Some(ElementTypeEnum::Scalar);
} else if *self == Self::VEC2 {
return Some(ElementTypeEnum::Vec2);
} else if *self == Self::VEC3 {
return Some(ElementTypeEnum::Vec3);
} else if *self == Self::VEC4 {
return Some(ElementTypeEnum::Vec4);
} else if *self == Self::MAT2 {
return Some(ElementTypeEnum::Mat2);
} else if *self == Self::MAT3 {
return Some(ElementTypeEnum::Mat3);
} else if *self == Self::MAT4 {
return Some(ElementTypeEnum::Mat4);
}
None
}
}
#[derive(Debug, Clone, Deserialize, IntoOwned)]
pub struct SparseIndices<'a> {
#[serde(rename = "bufferView")]
pub buffer_view: Idx<BufferView<'static>>,
#[serde(rename = "byteOffset")]
#[serde(default)]
pub byte_offset: u64,
#[serde(rename = "componentType")]
pub component_type: ComponentType,
#[serde(borrow)]
pub extensions: Option<Extensions<'a>>,
#[serde(borrow)]
pub extras: Option<Extras<'a>>,
}
#[derive(Debug, Clone, Deserialize, IntoOwned)]
pub struct SparseValues<'a> {
#[serde(rename = "bufferView")]
pub buffer_view: Idx<BufferView<'static>>,
#[serde(rename = "byteOffset")]
#[serde(default)]
pub byte_offset: u64,
#[serde(borrow)]
pub extensions: Option<Extensions<'a>>,
#[serde(borrow)]
pub extras: Option<Extras<'a>>,
}
#[derive(Debug, Clone, Deserialize, IntoOwned)]
pub struct Sparse<'a> {
pub count: u64,
pub indices: SparseIndices<'a>,
pub values: SparseValues<'a>,
#[serde(borrow)]
pub extensions: Option<Extensions<'a>>,
#[serde(borrow)]
pub extras: Option<Extras<'a>>,
}
#[derive(Debug, Clone, Deserialize, IntoOwned)]
pub struct Accessor<'a> {
#[serde(borrow)]
pub name: Option<Cow<'a, str>>,
#[serde(rename = "bufferView")]
pub buffer_view: Idx<BufferView<'static>>,
#[serde(rename = "byteOffset")]
#[serde(default)]
pub byte_offset: u64,
#[serde(rename = "type")]
#[serde(borrow)]
pub ty: ElementType<'a>,
#[serde(rename = "componentType")]
pub component_type: ComponentType,
#[serde(default)]
pub normalized: bool,
pub count: u64,
#[ownable(clone)]
pub max: Option<Vec<Number>>,
#[ownable(clone)]
pub min: Option<Vec<Number>>,
#[serde(borrow)]
pub sparse: Option<Sparse<'a>>,
#[serde(borrow)]
pub extensions: Option<Extensions<'a>>,
#[serde(borrow)]
pub extras: Option<Extras<'a>>,
}