1use crate::{EguiProbe, Style};
2
3impl<T> EguiProbe for Option<T>
4where
5 T: EguiProbe + Default,
6{
7 #[inline(always)]
8 fn probe(&mut self, ui: &mut egui::Ui, style: &Style) -> egui::Response {
9 option_probe_with(self, ui, style, T::default, |value, ui, style| {
10 value.probe(ui, style)
11 })
12 }
13
14 #[inline(always)]
15 fn iterate_inner(
16 &mut self,
17 ui: &mut egui::Ui,
18 f: &mut dyn FnMut(&str, &mut egui::Ui, &mut dyn EguiProbe),
19 ) {
20 if let Some(value) = self {
21 value.iterate_inner(ui, f);
22 }
23 }
24}
25
26#[inline(always)]
27pub fn option_probe_with<T>(
28 value: &mut Option<T>,
29 ui: &mut egui::Ui,
30 style: &Style,
31 default: impl FnOnce() -> T,
32 probe: impl FnOnce(&mut T, &mut egui::Ui, &Style) -> egui::Response,
33) -> egui::Response {
34 let mut changed = false;
35 let mut r = ui
36 .horizontal(|ui| {
37 let mut checked = value.is_some();
38
39 if ui.selectable_label(!checked, "None").clicked() {
40 checked = false;
41 }
42 if ui.selectable_label(checked, "Some").clicked() {
43 checked = true;
44 }
45
46 match (checked, value.is_some()) {
47 (true, false) => {
48 *value = Some(default());
49 changed = true;
50 }
51 (false, true) => {
52 *value = None;
53 changed = true;
54 }
55 _ => {}
56 }
57
58 if let Some(value) = value {
59 changed |= probe(value, ui, style).changed();
60 }
61 })
62 .response;
63
64 if changed {
65 r.mark_changed();
66 }
67
68 r
69}