dear_implot/context/
token.rs1use super::callbacks::PlotScopeGuard;
2use super::core::PlotContextBinding;
3use crate::sys;
4use dear_imgui_rs::{DrawListMut, Ui};
5use std::marker::PhantomData;
6use std::rc::Rc;
7
8pub struct PlotToken<'ui> {
12 binding: PlotContextBinding,
13 ui: &'ui Ui,
14 _scope: PlotScopeGuard,
15 _lifetime: PhantomData<&'ui ()>,
16}
17
18impl<'ui> PlotToken<'ui> {
19 pub(crate) fn new(binding: PlotContextBinding, ui: &'ui Ui) -> Self {
21 Self {
22 binding,
23 ui,
24 _scope: PlotScopeGuard::new(),
25 _lifetime: PhantomData,
26 }
27 }
28
29 pub fn end(self) {
34 }
36
37 pub fn plot_draw_list(&self) -> Option<DrawListMut<'_>> {
39 self.binding
40 .with_bound_context("dear-implot: PlotToken", || {
41 let draw_list = unsafe { sys::ImPlot_GetPlotDrawList() };
42 if draw_list.is_null() {
43 None
44 } else {
45 Some(unsafe { DrawListMut::from_raw_mut(self.ui, draw_list) })
46 }
47 })
48 }
49
50 pub fn push_plot_clip_rect(&self, expand: f32) -> PlotClipRectToken<'_> {
55 assert!(
56 expand.is_finite(),
57 "PlotToken::push_plot_clip_rect() expand must be finite"
58 );
59 self.binding
60 .with_bound_context("dear-implot: PlotToken", || {
61 unsafe { sys::ImPlot_PushPlotClipRect(expand) };
62 PlotClipRectToken {
63 binding: self.binding.clone(),
64 was_popped: false,
65 _lifetime: PhantomData,
66 _not_send_or_sync: PhantomData,
67 }
68 })
69 }
70}
71
72impl<'ui> Drop for PlotToken<'ui> {
73 fn drop(&mut self) {
74 let _ = self.binding.try_with_bound_context(|| unsafe {
75 sys::ImPlot_EndPlot();
76 });
77 }
78}
79
80#[must_use]
82pub struct PlotClipRectToken<'plot> {
83 binding: PlotContextBinding,
84 was_popped: bool,
85 _lifetime: PhantomData<&'plot ()>,
86 _not_send_or_sync: PhantomData<Rc<()>>,
87}
88
89impl PlotClipRectToken<'_> {
90 pub fn pop(mut self) {
92 self.pop_inner();
93 }
94
95 pub fn end(mut self) {
97 self.pop_inner();
98 }
99
100 fn pop_inner(&mut self) {
101 if self.was_popped {
102 panic!("Attempted to pop an ImPlot plot clip rect token twice.");
103 }
104 self.binding
105 .with_bound_context("dear-implot: PlotClipRectToken", || {
106 unsafe { sys::ImPlot_PopPlotClipRect() };
107 });
108 self.was_popped = true;
109 }
110}
111
112impl Drop for PlotClipRectToken<'_> {
113 fn drop(&mut self) {
114 if !self.was_popped {
115 let _ = self
116 .binding
117 .try_with_bound_context(|| unsafe { sys::ImPlot_PopPlotClipRect() });
118 self.was_popped = true;
119 }
120 }
121}