dear_implot3d/style/
item_arrays.rs1use crate::{Plot3DUi, sys};
2use std::borrow::Cow;
3
4#[derive(Debug, Clone, Default, PartialEq)]
6pub struct Plot3DItemArrayStyle<'a> {
7 line_colors: Option<Cow<'a, [u32]>>,
8 fill_colors: Option<Cow<'a, [u32]>>,
9 marker_sizes: Option<Cow<'a, [f32]>>,
10 marker_line_colors: Option<Cow<'a, [u32]>>,
11 marker_fill_colors: Option<Cow<'a, [u32]>>,
12}
13
14impl<'a> Plot3DItemArrayStyle<'a> {
15 pub fn new() -> Self {
17 Self::default()
18 }
19
20 pub fn with_line_colors(mut self, colors: &'a [u32]) -> Self {
22 self.line_colors = Some(Cow::Borrowed(colors));
23 self
24 }
25
26 pub fn with_fill_colors(mut self, colors: &'a [u32]) -> Self {
28 self.fill_colors = Some(Cow::Borrowed(colors));
29 self
30 }
31
32 pub fn with_marker_sizes(mut self, sizes: &'a [f32]) -> Self {
34 self.marker_sizes = Some(Cow::Borrowed(sizes));
35 self
36 }
37
38 pub fn with_marker_line_colors(mut self, colors: &'a [u32]) -> Self {
40 self.marker_line_colors = Some(Cow::Borrowed(colors));
41 self
42 }
43
44 pub fn with_marker_fill_colors(mut self, colors: &'a [u32]) -> Self {
46 self.marker_fill_colors = Some(Cow::Borrowed(colors));
47 self
48 }
49
50 fn apply_to_spec(&self, spec: &mut sys::ImPlot3DSpec_c) {
51 spec.LineColors = self
52 .line_colors
53 .as_ref()
54 .map_or(std::ptr::null_mut(), |colors| colors.as_ptr() as *mut _);
55 spec.FillColors = self
56 .fill_colors
57 .as_ref()
58 .map_or(std::ptr::null_mut(), |colors| colors.as_ptr() as *mut _);
59 spec.MarkerSizes = self
60 .marker_sizes
61 .as_ref()
62 .map_or(std::ptr::null_mut(), |sizes| sizes.as_ptr() as *mut _);
63 spec.MarkerLineColors = self
64 .marker_line_colors
65 .as_ref()
66 .map_or(std::ptr::null_mut(), |colors| colors.as_ptr() as *mut _);
67 spec.MarkerFillColors = self
68 .marker_fill_colors
69 .as_ref()
70 .map_or(std::ptr::null_mut(), |colors| colors.as_ptr() as *mut _);
71 }
72}
73
74struct ScopedNextPlot3DItemArrayStyle {
75 previous: Option<sys::ImPlot3DSpec_c>,
76 active: bool,
77}
78
79impl ScopedNextPlot3DItemArrayStyle {
80 fn restore_if_unused(&mut self) {
81 if !self.active {
82 return;
83 }
84
85 if crate::take_next_plot3d_spec().is_some() {
86 crate::set_next_plot3d_spec(self.previous.take());
87 }
88 self.active = false;
89 }
90}
91
92impl Drop for ScopedNextPlot3DItemArrayStyle {
93 fn drop(&mut self) {
94 self.restore_if_unused();
95 }
96}
97
98pub(crate) fn with_scoped_next_plot3d_item_array_style<'a, R>(
99 style: Plot3DItemArrayStyle<'a>,
100 f: impl FnOnce() -> R,
101) -> R {
102 let previous = crate::take_next_plot3d_spec();
103 let mut spec = previous.unwrap_or_else(crate::default_plot3d_spec);
104 style.apply_to_spec(&mut spec);
105 crate::set_next_plot3d_spec(Some(spec));
106
107 let mut guard = ScopedNextPlot3DItemArrayStyle {
108 previous,
109 active: true,
110 };
111 let out = f();
112 guard.restore_if_unused();
113 out
114}
115
116impl<'ui> Plot3DUi<'ui> {
117 pub fn with_next_plot3d_item_array_style<'a, R>(
122 &self,
123 style: Plot3DItemArrayStyle<'a>,
124 f: impl FnOnce(&Plot3DUi<'ui>) -> R,
125 ) -> R {
126 let _guard = self.bind();
127 with_scoped_next_plot3d_item_array_style(style, || f(self))
128 }
129}