| #![doc(html_root_url = "https://sergio.bz/rustdocs/yansi")] |
| |
| //! A dead simple ANSI terminal color painting library. |
| //! |
| //! # Usage |
| //! |
| //! Usage is best illustrated via a quick example: |
| //! |
| //! ```rust |
| //! use yansi::{Paint, Color}; |
| //! |
| //! println!("Testing, {}, {}, {}!", |
| //! Paint::red(1), |
| //! Paint::green(2).bold().underline(), |
| //! Paint::blue("3").bg(Color::White).italic()); |
| //! ``` |
| //! |
| //! ## Paint |
| //! |
| //! The main entry point into this library is the [`Paint`] type. `Paint` |
| //! encapsulates a value of any type that implements the [`Display`] or |
| //! [`Debug`] trait. When a `Paint` is `Display`ed or `Debug`ed, the appropriate |
| //! ANSI escape characters are emitted before and after the wrapped type's `fmt` |
| //! implementation. |
| //! |
| //! `Paint` can be constructed via [a myriad of methods]. In addition to these |
| //! constructors, you can also use the [`color.paint()`](Color::paint()) method |
| //! on a given [`Color`] value to construct a `Paint` type. Both of these |
| //! approaches are shown below: |
| //! |
| //! ```rust |
| //! use yansi::Paint; |
| //! use yansi::Color::Red; |
| //! |
| //! println!("I'm {}!", Paint::red("red").bold()); |
| //! println!("I'm also {}!", Red.paint("red").bold()); |
| //! ``` |
| //! [`Display`]: ::std::fmt::Display |
| //! [`Debug`]: ::std::fmt::Debug |
| //! [a myriad of methods]: struct.Paint.html#unstyled-constructors |
| //! |
| //! ## Styling |
| //! |
| //! Modifications to the styling of an item can be made via [a number of |
| //! chainable methods] on `Paint`. |
| //! |
| //! ```rust |
| //! use yansi::Paint; |
| //! |
| //! Paint::new("hi").underline().invert().italic().dimmed().bold(); |
| //! ``` |
| //! |
| //! Styling can also be created independently from a `Paint` structure via the |
| //! [`Style`] structure. This allows common styling to be stored and reused. A |
| //! `Style` can be applied via the [`style.paint()`] method or the |
| //! [`paint.with_style()`] method: |
| //! |
| //! ```rust |
| //! use yansi::{Paint, Color, Style}; |
| //! |
| //! // A bold, itatlic style with red foreground. |
| //! let alert = Style::new(Color::Red).bold().italic(); |
| //! |
| //! // Using `style.paint()`; this is preferred. |
| //! println!("Alert! {}", alert.paint("This is serious business!")); |
| //! println!("Hi! {}", alert.underline().paint("Super serious!")); |
| //! |
| //! // Using `paint.with_style()`. |
| //! println!("Alert! {}", Paint::new("Yet another.").with_style(alert)); |
| //! ``` |
| //! |
| //! [a number of chainable methods]: struct.Paint.html#setters |
| //! [`style.paint()`]: Style::paint() |
| //! [`paint.with_style()`]: Paint::with_style() |
| //! |
| //! # Disabling |
| //! |
| //! Painting can be disabled globally via the [`Paint::disable()`] method. When |
| //! painting is disabled, the `Display` and `Debug` implementations for `Paint` |
| //! will emit the `Display` or `Debug` of the contained object and nothing else. |
| //! Painting can be reenabled via the [`Paint::enable()`] method. |
| //! |
| //! One potential use of this feature is to allow users to control color ouput |
| //! via an environment variable. For instance, to disable coloring if the |
| //! `CLICOLOR` variable is set to `0`, you might write: |
| //! |
| //! ```rust |
| //! # { if false { // we don't actually want to disable coloring |
| //! use yansi::Paint; |
| //! |
| //! if let Ok(true) = std::env::var("CLICOLOR").map(|v| v == "0") { |
| //! Paint::disable(); |
| //! } |
| //! # } } |
| //! ``` |
| //! |
| //! ## Masking |
| //! |
| //! Items can be arbitrarily _masked_. When an item is masked and painting is |
| //! disabled, the `Display` and `Debug` implementations of `Paint` write |
| //! nothing. This allows you to selectively omit output when painting is |
| //! disabled. Values can be masked using the [`Paint::masked()`] and |
| //! [`Style::masked()`]constructors or [`paint.mask()`] and [`style.mask()`] |
| //! style setters. |
| //! |
| //! [`paint.mask()`]: Paint::mask() |
| //! [`style.mask()`]: Style::mask() |
| //! |
| //! One use for this feature is to print certain characters only when painting |
| //! is enabled. For instance, you might wish to emit the 🎨 emoji when |
| //! coloring is enabled but not otherwise. This can be accomplished by masking |
| //! the emoji: |
| //! |
| //! ```rust |
| //! use yansi::Paint; |
| //! |
| //! println!("I like colors!{}", Paint::masked(" 🎨")); |
| //! ``` |
| //! |
| //! This will print "I like colors! 🎨" when painting is enabled and "I like |
| //! colors!" when painting is disabled. |
| //! |
| //! ## Wrapping |
| //! |
| //! Styling can be set to _wrap_ existing styles using either the |
| //! [`Paint::wrapping()`] constructor or the [`paint.wrap()`] and |
| //! [`style.wrap()`] style setters. When a style is _wrapping_, all color |
| //! resets written out by the internal item's `Display` or `Debug` |
| //! implementation are set to the styling of the wrapping style itself. In other |
| //! words, the "default" style of the wrapped item is modified to be the |
| //! wrapping style. This allows for easy wrapping of other colored text. Without |
| //! this feature, the console would reset styling to the terminal's default |
| //! style instead of the wrapping style. |
| //! |
| //! [`paint.wrap()`]: Paint::wrap() |
| //! [`style.wrap()`]: Style::wrap() |
| //! |
| //! One use for this feature is to ensure that styling is consistently set |
| //! across items that may already be styled, such as when logging. |
| //! |
| //! ```rust |
| //! use yansi::{Paint, Color}; |
| //! |
| //! let inner = format!("{} and {}", Paint::red("Stop"), Paint::green("Go")); |
| //! println!("Hey! {}", Paint::wrapping(inner).fg(Color::Blue)); |
| //! ``` |
| //! |
| //! This will print 'Hey!' unstyled, "Stop" in red, "and" in blue, and "Go" in |
| //! green. Without wrapping, "and" would be unstyled as `Paint::red()` resets |
| //! the style after printing the internal item. |
| //! |
| //! # Windows |
| //! |
| //! Coloring is supported on Windows beginning with the Windows 10 anniversary |
| //! update. Since this update, Windows consoles support ANSI escape sequences. |
| //! This support, however, must be explicitly enabled. `yansi` provides the |
| //! [`Paint::enable_windows_ascii()`] method to enable ASCII support on Windows |
| //! consoles when available. |
| //! |
| //! ```rust |
| //! use yansi::Paint; |
| //! |
| //! // Enable ASCII escape sequence support on Windows consoles. |
| //! Paint::enable_windows_ascii(); |
| //! ``` |
| //! |
| //! You may wish to disable coloring on unsupported Windows consoles to avoid |
| //! emitting unrecognized ASCII escape sequences: |
| //! |
| //! ```rust |
| //! use yansi::Paint; |
| //! |
| //! if cfg!(windows) && !Paint::enable_windows_ascii() { |
| //! Paint::disable(); |
| //! } |
| //! ``` |
| //! |
| //! [`Paint::enable_windows_ascii()`]: Paint::enable_windows_ascii() |
| //! |
| //! # Why? |
| //! |
| //! Several terminal coloring libraries exist ([`ansi_term`], [`colored`], |
| //! [`term_painter`], to name a few), begging the question: why yet another? |
| //! Here are a few reasons: |
| //! |
| //! * This library is _much_ simpler: there are three types! |
| //! * Unlike [`ansi_term`] or [`colored`], _any_ type implementing `Display` |
| //! or `Debug` can be stylized, not only strings. |
| //! * Styling can be enabled and disabled globally, on the fly. |
| //! * Arbitrary items can be [_masked_] for selective disabling. |
| //! * Styling can [_wrap_] any arbitrarily styled item. |
| //! * Typically only one type needs to be imported: [`Paint`]. |
| //! * Zero dependencies. It really is simple. |
| //! * The name `yansi` is pretty short. |
| //! |
| //! All that being said, this library borrows API ideas from the three libraries |
| //! as well as implementation details from [`ansi_term`]. |
| //! |
| //! [`ansi_term`]: https://crates.io/crates/ansi_term |
| //! [`colored`]: https://crates.io/crates/colored |
| //! [`term_painter`]: https://crates.io/crates/term-painter |
| //! [_masked_]: #masking |
| //! [_wrap_]: #wrapping |
| |
| #[macro_use] mod docify; |
| #[macro_use] mod macros; |
| |
| #[cfg(test)] mod tests; |
| mod windows; |
| mod paint; |
| mod style; |
| mod color; |
| |
| pub use color::Color; |
| pub use style::Style; |
| pub use paint::Paint; |