widgetkit_render/
surface.rs1use crate::{Canvas, raw::{Frame, Rasterizer}};
2use widgetkit_core::{Color, Error, Result};
3
4pub trait RenderSurface {
5 fn size(&self) -> (u32, u32);
6 fn present(&mut self, pixels: &[Color]) -> Result<()>;
7}
8
9pub trait Renderer: Send {
10 fn render_canvas(&mut self, canvas: Canvas, surface: &mut dyn RenderSurface) -> Result<()>;
11}
12
13pub struct SoftwareRenderer {
14 pixels: Vec<Color>,
15}
16
17impl SoftwareRenderer {
18 pub fn new() -> Self {
19 Self { pixels: Vec::new() }
20 }
21
22 fn ensure_buffer(&mut self, width: u32, height: u32) -> Result<()> {
23 let len = usize::try_from(width)
24 .ok()
25 .and_then(|w| usize::try_from(height).ok().map(|h| w.saturating_mul(h)))
26 .ok_or_else(|| Error::render("surface dimensions exceed addressable memory"))?;
27 if self.pixels.len() != len {
28 self.pixels.resize(len, Color::TRANSPARENT);
29 }
30 Ok(())
31 }
32}
33
34impl Default for SoftwareRenderer {
35 fn default() -> Self {
36 Self::new()
37 }
38}
39
40impl Renderer for SoftwareRenderer {
41 fn render_canvas(&mut self, canvas: Canvas, surface: &mut dyn RenderSurface) -> Result<()> {
42 let (width, height) = surface.size();
43 self.ensure_buffer(width, height)?;
44 let scene = canvas.into_scene();
45 let frame = Frame::new(width, height, &mut self.pixels);
46 let mut raster = Rasterizer::new(frame);
47 raster.execute(scene);
48 drop(raster);
49 surface.present(&self.pixels)
50 }
51}