1use crate::{Alternate, DisplayPair};
2use core::{
3 fmt::{DebugSet, Display, Formatter, Result as FmtResult},
4 format_args,
5};
6
7type StructEntrier = fn(&mut DebugSet<'_, '_>, &dyn Display, &dyn Display);
8
9fn usual_struct_entrier(w: &mut DebugSet, k: &dyn Display, v: &dyn Display) {
10 w.entry(&format_args!("{}: {}", k, v));
11}
12
13fn alternative_struct_entrier(w: &mut DebugSet, k: &dyn Display, v: &dyn Display) {
14 w.entry(&format_args!("{}: {:#}", k, v));
15}
16
17fn null_struct_entrier(_: &mut DebugSet, _: &dyn Display, _: &dyn Display) {}
18
19fn inherit_entrier(inherited_value: bool) -> StructEntrier {
20 match inherited_value {
21 false => usual_struct_entrier,
22 true => alternative_struct_entrier,
23 }
24}
25
26#[cfg_attr(docsrs, doc(cfg(feature = "struct")))]
28pub struct StructShow<'a, 'b> {
29 wrapper: DebugSet<'a, 'b>,
30 entrier: StructEntrier,
31 inherited_value: bool,
32}
33
34impl<'a, 'b> StructShow<'a, 'b> {
35 fn choose_entrier(alternate: Alternate, inherited_value: bool) -> StructEntrier {
36 match alternate {
37 Alternate::OneLine => usual_struct_entrier,
38 Alternate::Pretty => alternative_struct_entrier,
39 Alternate::Inherit => inherit_entrier(inherited_value),
40 }
41 }
42
43 pub fn new(formatter: &'a mut Formatter<'b>, alternate: Alternate) -> Self {
45 let inherited_value = formatter.alternate();
46 let entrier = Self::choose_entrier(alternate, inherited_value);
47 Self {
48 wrapper: formatter.debug_set(),
49 entrier,
50 inherited_value,
51 }
52 }
53
54 pub fn inherit(formatter: &'a mut Formatter<'b>) -> Self {
56 let inherited_value = formatter.alternate();
57 let entrier = inherit_entrier(inherited_value);
58 Self {
59 wrapper: formatter.debug_set(),
60 entrier,
61 inherited_value,
62 }
63 }
64
65 pub fn field(&mut self, key: &dyn Display, val: &dyn Display) -> &mut Self {
67 (self.entrier)(&mut self.wrapper, key, val);
68 self
69 }
70
71 pub fn field_override(
73 &mut self,
74 key: &dyn Display,
75 val: &dyn Display,
76 alternate: Alternate,
77 ) -> &mut Self {
78 if null_struct_entrier as usize != self.entrier as usize {
81 let entrier = Self::choose_entrier(alternate, self.inherited_value);
82 entrier(&mut self.wrapper, key, val);
83 }
84 self
85 }
86
87 pub fn field_opt<T: Display>(&mut self, key: &dyn Display, val: &Option<T>) -> &mut Self {
89 if let Some(actual_value) = val {
90 self.field(key, actual_value);
91 }
92 self
93 }
94
95 pub fn field_opt_override<T: Display>(
97 &mut self,
98 key: &dyn Display,
99 val: &Option<T>,
100 alternate: Alternate,
101 ) -> &mut Self {
102 if let Some(actual_value) = val {
103 self.field_override(key, actual_value, alternate);
104 }
105 self
106 }
107
108 pub fn finish(&mut self) -> FmtResult {
110 self.entrier = null_struct_entrier;
111 self.wrapper.finish()
112 }
113
114 pub fn fields(&mut self, fields: &[(&dyn Display, &dyn Display)]) -> &mut Self {
116 self.fields_from_iter(fields.iter())
117 }
118
119 pub fn fields_from_iter<'c, I>(&mut self, fields: I) -> &mut Self
121 where
122 I: Iterator + 'c,
123 I::Item: DisplayPair,
124 {
125 fields.for_each(|p| (self.entrier)(&mut self.wrapper, p.left(), p.rifgt()));
126 self
127 }
128
129 pub fn alternate(&self) -> bool {
131 self.inherited_value
132 }
133}
134
135#[cfg_attr(docsrs, doc(cfg(feature = "struct")))]
138pub fn display_struct(f: &mut Formatter<'_>, fields: &[(&dyn Display, &dyn Display)]) -> FmtResult {
139 StructShow::new(f, Alternate::Inherit)
140 .fields(fields)
141 .finish()
142}
143
144#[cfg_attr(docsrs, doc(cfg(feature = "struct")))]
147pub fn display_struct_from_iter<'c, I>(f: &mut Formatter<'_>, fields: I) -> FmtResult
148where
149 I: Iterator + 'c,
150 I::Item: DisplayPair,
151{
152 StructShow::new(f, Alternate::Inherit)
153 .fields_from_iter(fields)
154 .finish()
155}