use diaphragm_core::{ styles::{Pattern, DefinedDashStyle}, text::{DefinedFontDescription, FontDescription}, Renderer, }; pub struct CairoRenderer { ctx: cairo::Context, } impl CairoRenderer { pub fn new() -> Self { // TODO: properly let surface = cairo::SvgSurface::for_stream(1920., 1080., std::io::stdout()).unwrap(); let ctx = cairo::Context::new(&surface).unwrap(); Self { ctx } } } impl Renderer for CairoRenderer { fn move_to(&mut self, x: f64, y: f64) { self.ctx.move_to(x, y) } fn stroke(&mut self) { self.ctx.stroke().unwrap(); } fn fill(&mut self) { self.ctx.fill().unwrap(); } fn fill_preserve(&mut self) { self.ctx.fill_preserve().unwrap(); } fn set_pattern(&mut self, pattern: &Pattern) { match pattern { Pattern::Solid(color) => { let (red, green, blue, alpha) = color.rgba(); self.ctx.set_source_rgba(red, green, blue, alpha) } Pattern::None => {} _ => panic!("Unhandled pattern"), } } fn set_dash(&mut self, dash: &DefinedDashStyle) { self.ctx.set_dash(dash.dashes(), dash.offset()); } fn clear_dash(&mut self) { self.ctx.set_dash(&[], 0.); } fn set_line_width(&mut self, width: f64) { self.ctx.set_line_width(width); } fn line_to(&mut self, x: f64, y: f64) { self.ctx.line_to(x, y) } fn rectangle(&mut self, x: f64, y: f64, width: f64, height: f64) { self.ctx.rectangle(x, y, width, height); } fn text_extents(&self, text: &str, font: &FontDescription) -> (f64, f64) { let layout = pangocairo::create_layout(&self.ctx); let font_desc = pango::FontDescription::from_string(&font.family); layout.set_font_description(Some(&font_desc)); layout.set_markup(text); //let (extents, _) = layout.get_pixel_extents(); //(extents.width as f64, extents.height as f64) // TODO: get height from the baseline let mut layout_iter = layout.iter(); let _height = loop { if layout_iter.at_last_line() { break layout_iter.baseline(); } layout_iter.next_line(); }; // TODO: Probably should use the logical extents, but it has weird width let (_, extents) = layout.pixel_extents(); //let (extents, _) = layout.get_pixel_extents(); (extents.width() as f64, extents.height() as f64) //let (width, height) = layout.get_pixel_size(); //(width as f64, height as f64) } fn show_text(&mut self, text: &str, font: &DefinedFontDescription) { let layout = pangocairo::create_layout(&self.ctx); let mut font_desc = pango::FontDescription::from_string(&font.family); // TODO: I have no fucking idea why font_desc.set_size((font.size * 600.) as _); //font_desc.set_size((font.size * 700.) as _); //font_desc.set_absolute_size(font.size * 800.); layout.set_font_description(Some(&font_desc)); layout.set_markup(text); //self.ctx.set_font_size(dbg!(font.size)); pangocairo::show_layout(&self.ctx, &layout); } }