use crate::{ Axis, AxisT, IdLike, Len, RenderedText, Size, TextAttrs, TextBuffer, TextData, Textures, UiVec2, WidgetAxisFns, WidgetId, Widgets, XAxis, YAxis, ui::cache::Cache, util::Vec2, }; pub struct SizeCtx<'a> { pub text: &'a mut TextData, pub textures: &'a mut Textures, pub(super) source: WidgetId, pub(super) widgets: &'a Widgets, pub(super) cache: &'a mut Cache, /// TODO: should this be pub? rn used for sized pub outer: UiVec2, pub(super) output_size: Vec2, pub(super) id: WidgetId, } impl SizeCtx<'_> { pub fn id(&self) -> &WidgetId { &self.id } pub fn source(&self) -> &WidgetId { &self.source } pub(super) fn len_inner(&mut self, id: WidgetId) -> Len { if let Some((_, len)) = self.cache.size.axis::().get(&id) { return *len; } let len = self .widgets .get_dyn_dynamic(id) .desired_len::(&mut SizeCtx { text: self.text, textures: self.textures, source: self.source, widgets: self.widgets, cache: self.cache, outer: self.outer, output_size: self.output_size, id, }); self.cache.size.axis::().insert(id, (self.outer, len)); len } pub fn width(&mut self, id: impl IdLike) -> Len { self.len_inner::(id.id()) } pub fn height(&mut self, id: impl IdLike) -> Len { self.len_inner::(id.id()) } pub fn len_axis(&mut self, id: impl IdLike, axis: Axis) -> Len { match axis { Axis::X => self.width(id), Axis::Y => self.height(id), } } pub fn size(&mut self, id: impl IdLike) -> Size { let id = id.id(); Size { x: self.width(id), y: self.height(id), } } pub fn px_size(&mut self) -> Vec2 { self.outer.to_abs(self.output_size) } pub fn output_size(&mut self) -> Vec2 { self.output_size } pub fn draw_text(&mut self, buffer: &mut TextBuffer, attrs: &TextAttrs) -> RenderedText { self.text.draw(buffer, attrs, self.textures) } pub fn label(&self, id: WidgetId) -> &String { self.widgets.label(id) } }