use bevy_ecs::{
prelude::{Entity, In},
query::QueryEntityError,
};
use smallvec::SmallVec;
use thiserror::Error;
use crate::{BufferAccessMut, BufferKey};
#[derive(Debug, Error)]
pub enum BufferAccessError {
#[error("The query does not match the entity {0}")]
QueryDoesNotMatch(Entity),
#[error("The entity {0} does not exist")]
EntityDoesNotExist(Entity),
#[error("The entity {0} was requested mutably more than once")]
AliasedMutability(Entity),
}
pub(super) fn consume_buffer<const N: usize, T>(
In(key): In<BufferKey<T>>,
mut access: BufferAccessMut<T>,
) -> SmallVec<[T; N]>
where
T: 'static + Send + Sync,
{
let Ok(mut buffer) = access.get_mut(&key) else {
return SmallVec::new();
};
buffer.drain(..).collect()
}
pub fn push_into_buffer<T: 'static + Send + Sync>(
In((input, key)): In<(T, BufferKey<T>)>,
mut access: BufferAccessMut<T>,
) -> Result<(), BufferAccessError> {
access
.get_mut(&key)
.map_err(|err| match err {
QueryEntityError::QueryDoesNotMatch(e, _) => BufferAccessError::QueryDoesNotMatch(e),
QueryEntityError::EntityDoesNotExist(e) => {
BufferAccessError::EntityDoesNotExist(e.entity)
}
QueryEntityError::AliasedMutability(e) => BufferAccessError::AliasedMutability(e),
})?
.push(input);
Ok(())
}