use log::debug;
use rocketsplash_formats::{
CellStyle, Splash as SplashFormat, SPLASH_MIN_SUPPORTED, SPLASH_VERSION,
};
use crate::render::{RenderBuffer, RenderCell};
use crate::splash::Splash;
use crate::{Error, TextStyle};
pub fn load_splash_from_bytes(bytes: &[u8]) -> Result<Splash, Error> {
let splash: SplashFormat =
rmp_serde::from_slice(bytes).map_err(|err| Error::InvalidFormat {
message: err.to_string(),
})?;
if splash.version < SPLASH_MIN_SUPPORTED || splash.version > SPLASH_VERSION {
return Err(Error::UnsupportedVersion {
format: "splash".to_string(),
found: splash.version,
min_supported: SPLASH_MIN_SUPPORTED,
current: SPLASH_VERSION,
});
}
splash
.validate()
.map_err(|message| Error::InvalidFormat { message })?;
let width = splash.width as usize;
let height = splash.height as usize;
let mut buffer = RenderBuffer::new(width, height);
for (idx, cell) in splash.cells.iter().enumerate() {
if idx >= buffer.cells.len() {
break;
}
let mut render_cell = RenderCell::empty();
render_cell.ch = cell.ch;
render_cell.fg = cell.fg;
render_cell.bg = cell.bg;
render_cell.style = to_text_style(cell.style);
render_cell.opacity = if cell.ch == ' ' { 0 } else { 255 };
buffer.cells[idx] = render_cell;
}
debug!("Loaded splash {} ({}x{})", splash.meta.name, width, height);
Ok(Splash {
meta: splash.meta,
buffer,
})
}
fn to_text_style(style: CellStyle) -> TextStyle {
let mut text_style = TextStyle::empty();
if style.contains(CellStyle::BOLD) {
text_style |= TextStyle::BOLD;
}
if style.contains(CellStyle::ITALIC) {
text_style |= TextStyle::ITALIC;
}
if style.contains(CellStyle::UNDERLINE) {
text_style |= TextStyle::UNDERLINE;
}
if style.contains(CellStyle::REVERSE) {
text_style |= TextStyle::REVERSE;
}
text_style
}