clap_builder/output/
fmt.rs

1use crate::builder::StyledStr;
2use crate::util::color::ColorChoice;
3
4#[derive(Copy, Clone, Debug, PartialEq, Eq)]
5pub(crate) enum Stream {
6    Stdout,
7    Stderr,
8}
9
10#[derive(Clone, Debug)]
11pub(crate) struct Colorizer {
12    stream: Stream,
13    #[allow(unused)]
14    color_when: ColorChoice,
15    content: StyledStr,
16}
17
18impl Colorizer {
19    pub(crate) fn new(stream: Stream, color_when: ColorChoice) -> Self {
20        Colorizer {
21            stream,
22            color_when,
23            content: Default::default(),
24        }
25    }
26
27    pub(crate) fn with_content(mut self, content: StyledStr) -> Self {
28        self.content = content;
29        self
30    }
31}
32
33/// Printing methods.
34impl Colorizer {
35    #[cfg(feature = "color")]
36    pub(crate) fn print(&self) -> std::io::Result<()> {
37        let color_when = match self.color_when {
38            ColorChoice::Always => anstream::ColorChoice::Always,
39            ColorChoice::Auto => anstream::ColorChoice::Auto,
40            ColorChoice::Never => anstream::ColorChoice::Never,
41        };
42
43        let mut stdout;
44        let mut stderr;
45        let writer: &mut dyn std::io::Write = match self.stream {
46            Stream::Stderr => {
47                stderr = anstream::AutoStream::new(std::io::stderr().lock(), color_when);
48                &mut stderr
49            }
50            Stream::Stdout => {
51                stdout = anstream::AutoStream::new(std::io::stdout().lock(), color_when);
52                &mut stdout
53            }
54        };
55
56        self.content.write_to(writer)
57    }
58
59    #[cfg(not(feature = "color"))]
60    pub(crate) fn print(&self) -> std::io::Result<()> {
61        // [e]println can't be used here because it panics
62        // if something went wrong. We don't want that.
63        match self.stream {
64            Stream::Stdout => {
65                let stdout = std::io::stdout();
66                let mut stdout = stdout.lock();
67                self.content.write_to(&mut stdout)
68            }
69            Stream::Stderr => {
70                let stderr = std::io::stderr();
71                let mut stderr = stderr.lock();
72                self.content.write_to(&mut stderr)
73            }
74        }
75    }
76}
77
78/// Color-unaware printing. Never uses coloring.
79impl std::fmt::Display for Colorizer {
80    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
81        self.content.fmt(f)
82    }
83}