use femtovg::ImageFlags; use femtovg::PixelFormat::Rgba8; use femtovg::{renderer::OpenGl, Canvas, Paint}; use num_traits::{Num, NumOps}; use std::path::Path; use std::sync::Arc; use std::sync::Mutex; use crate::pipeline::offscreen_renderer::CanvasWrapper; use crate::render::cms::CMS; use crate::render::{LayerImpl, Target}; use crate::render::{LayerImplSync, TargetType}; use crate::{ data::{AsyncDataLoader, DataLoader, Radar2d}, render::{Layer, Render}, }; use super::{ color_mapper::ColorMapper, grid_field_renderer::{GridFieldRenderer, GridLayerImpl}, }; impl Layer { pub fn grid_render_layer(data: Radar2d, layer_name: String, color_map: CMAP) -> Self where T: std::fmt::Debug + Num + NumOps + PartialOrd + Copy + Clone + 'static + Send + Sync, CMAP: ColorMapper + 'static, { Self::new( true, |s, render, _| { let mut c = render.get_canvas(); let c = c.as_mut().unwrap(); let render_target = s.render_target(); let mut unlock_target = render_target.lock().unwrap(); let image_id = if let Some(target) = unlock_target.as_mut() { let result_id = match target.target { TargetType::ImageId(id) => id, TargetType::Mem(ref mem) => { let converted = c .load_image_mem(&mem, femtovg::ImageFlags::empty()) .unwrap(); target.set_target(TargetType::ImageId(converted)); converted } }; let (x, y) = target.size(&render); let (ox, oy) = target.origin(&render); Some((result_id, (x, y), (ox, oy))) } else { None }; if let Some((id, (x, y), (ox, oy))) = image_id { if let Ok(_) = c.image_size(id) { let painter = Paint::image(id, ox, oy, x, y, 0.0, 1.0); let mut path = femtovg::Path::new(); path.rect(ox, oy, x, y); c.fill_path(&path, &painter); } } }, layer_name, Some( |renderer: LayerImplSync, c: Arc>, cms: CMS| async move { let mut canvas = c.lock().unwrap(); let renderer = renderer.lock().unwrap(); let img = renderer.draw(&mut canvas, cms).unwrap(); img }, ), Some(GridLayerImpl::new(GridFieldRenderer::new(color_map), data)), ) } pub fn grid_render_layer_with_path( path: impl AsRef, layer_name: String, loader: LOADER, color_map: CMAP, ) -> Self where T: Num + NumOps + PartialOrd + Copy + Clone + 'static + std::fmt::Debug + Sync + Send, CMAP: ColorMapper + 'static, LOADER: DataLoader>, { let data = loader.load(path).unwrap(); self::Layer::grid_render_layer(data, layer_name, color_map) } pub async fn grid_render_layer_with_path_async( path: impl AsRef + Send, layer_name: String, loader: LOADER, color_map: CMAP, ) -> Self where T: Num + NumOps + PartialOrd + Copy + Clone + 'static + std::fmt::Debug + Send + Sync, CMAP: ColorMapper + 'static, LOADER: AsyncDataLoader>, { let data = loader.load(path).await.unwrap(); self::Layer::grid_render_layer(data, layer_name, color_map) } }