use std::collections::HashMap;
use std::sync::Arc;
use crate::buf::{OpaqueValue, RasterBuf, ScalarField};
use crate::value::ScalarValue;
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
pub struct TileId {
pub z: u8,
pub x: u32,
pub y: u32,
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
pub struct CanvasInfo {
pub tile_size: u32,
pub pad: u32,
}
impl CanvasInfo {
pub fn padded_size(&self) -> u32 {
self.tile_size + 2 * self.pad
}
}
#[derive(Debug, Clone)]
pub enum Asset {
Image(Arc<RasterBuf>),
Brush(OpaqueValue),
Features(OpaqueValue),
ScalarField(Arc<ScalarField>),
}
#[derive(Debug, thiserror::Error)]
pub enum AssetError {
#[error("asset not found: `{0}`")]
NotFound(String),
#[error("asset decode failed for `{src}`: {msg}")]
Decode { src: String, msg: String },
#[error("asset error: {0}")]
Other(String),
}
pub trait AssetLoader: Send + Sync {
fn load(&self, name: &str) -> Result<Asset, AssetError>;
fn hash(&self, _name: &str) -> u128 {
0
}
}
pub struct NoAssets;
impl AssetLoader for NoAssets {
fn load(&self, name: &str) -> Result<Asset, AssetError> {
Err(AssetError::NotFound(name.to_string()))
}
}
#[derive(Debug, Default, Clone)]
pub struct ParamValues {
pub values: HashMap<String, ScalarValue>,
}
impl ParamValues {
pub fn new() -> Self {
Self::default()
}
pub fn set(&mut self, name: impl Into<String>, value: ScalarValue) {
self.values.insert(name.into(), value);
}
pub fn get(&self, name: &str) -> Option<ScalarValue> {
self.values.get(name).copied()
}
}
pub struct EvalCtx<'a> {
pub tile: TileId,
pub canvas: CanvasInfo,
pub assets: &'a dyn AssetLoader,
pub params: &'a ParamValues,
pub rng_seed: u64,
}
#[derive(Debug, thiserror::Error)]
pub enum EvalError {
#[error("input port `{0}` was not supplied")]
MissingInput(String),
#[error("input `{port}` has wrong kind: expected {expected:?}, got {got:?}")]
InputKindMismatch {
port: String,
expected: crate::port::PortKind,
got: crate::port::PortKind,
},
#[error(transparent)]
Asset(#[from] AssetError),
#[error("{0}")]
Other(String),
}