use std::path::Path;
use serde::Deserialize;
use crate::SpriteModeMap;
#[derive(Debug, Clone, Default, Deserialize)]
pub struct PlayerPresentationDoc {
#[serde(default)]
pub player_presentation: PlayerPresentationConfig,
}
#[derive(Debug, Clone, Default, Deserialize)]
pub struct PlayerPresentationConfig {
#[serde(default)]
pub tile_id: Option<String>,
#[serde(default)]
pub paperdoll_ref: Option<String>,
#[serde(default)]
pub sprite_modes: SpriteModeMap,
}
impl PlayerPresentationConfig {
pub fn empty() -> Self {
Self::default()
}
}
pub fn default_player_presentation_path() -> Option<std::path::PathBuf> {
let mut dir = std::env::current_dir().ok()?;
for _ in 0..6 {
let candidate = dir.join("assets/gfx/player-presentation.yaml");
if candidate.is_file() {
return Some(candidate);
}
if !dir.pop() {
break;
}
}
None
}
pub fn load_player_presentation(
path: impl AsRef<Path>,
) -> anyhow::Result<PlayerPresentationConfig> {
let raw = std::fs::read_to_string(path.as_ref())?;
let doc: PlayerPresentationDoc = serde_yaml::from_str(&raw)?;
Ok(doc.player_presentation)
}
pub fn load_player_presentation_default() -> PlayerPresentationConfig {
default_player_presentation_path()
.and_then(|p| load_player_presentation(&p).ok())
.unwrap_or_default()
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn loads_repo_default() {
let path = default_player_presentation_path().expect("player-presentation.yaml");
let cfg = load_player_presentation(&path).expect("parse");
assert!(cfg.tile_id.is_some() || !cfg.sprite_modes.is_empty());
}
}