summaryrefslogtreecommitdiffstats
path: root/termcolor
diff options
context:
space:
mode:
authorAndrew Gallant <jamslam@gmail.com>2018-02-10 18:42:35 -0500
committerAndrew Gallant <jamslam@gmail.com>2018-02-10 22:28:12 -0500
commit2d68054b1da6ba7515118bbe98c80e4c5330cad5 (patch)
treef7dfd61d36b36c1dbf86427e17258f303044b8a9 /termcolor
parent65a63788bc2e785b879493725283d1a22e314bf2 (diff)
termcolor: support ANSI in Windows terminals
This commit uses the new virtual terminal processing feature in Windows 10 to enable the use of ANSI escape codes to color ripgrep's output. This technique is preferred over the console APIs because it seems like where the future is heading, but also because it avoids needing to use an intermediate buffer to deal with the Windows console in a multithreaded environment.
Diffstat (limited to 'termcolor')
-rw-r--r--termcolor/src/lib.rs23
1 files changed, 17 insertions, 6 deletions
diff --git a/termcolor/src/lib.rs b/termcolor/src/lib.rs
index 72b276f9..13b9fe24 100644
--- a/termcolor/src/lib.rs
+++ b/termcolor/src/lib.rs
@@ -239,7 +239,7 @@ impl io::Write for IoStandardStream {
}
}
-/// Same rigmarole for the locked variants of the standard streams.
+// Same rigmarole for the locked variants of the standard streams.
enum IoStandardStreamLock<'a> {
StdoutLock(io::StdoutLock<'a>),
@@ -328,14 +328,17 @@ impl StandardStream {
/// the `WriteColor` trait.
#[cfg(windows)]
fn create(sty: StandardStreamType, choice: ColorChoice) -> StandardStream {
- let con = match sty {
+ let mut con = match sty {
StandardStreamType::Stdout => wincolor::Console::stdout(),
StandardStreamType::Stderr => wincolor::Console::stderr(),
};
let is_win_console = con.is_ok();
+ let is_console_virtual = con.as_mut().map(|con| {
+ con.set_virtual_terminal_processing(true).is_ok()
+ }).unwrap_or(false);
let wtr =
if choice.should_attempt_color() {
- if choice.should_ansi() {
+ if choice.should_ansi() || is_console_virtual {
WriterInner::Ansi(Ansi(IoStandardStream::new(sty)))
} else if let Ok(console) = con {
WriterInner::Windows {
@@ -612,10 +615,18 @@ impl BufferWriter {
/// the buffers themselves.
#[cfg(windows)]
fn create(sty: StandardStreamType, choice: ColorChoice) -> BufferWriter {
- let con = match sty {
+ let mut con = match sty {
StandardStreamType::Stdout => wincolor::Console::stdout(),
StandardStreamType::Stderr => wincolor::Console::stderr(),
- }.ok().map(Mutex::new);
+ }.ok();
+ let is_console_virtual = con.as_mut().map(|con| {
+ con.set_virtual_terminal_processing(true).is_ok()
+ }).unwrap_or(false);
+ // If we can enable ANSI on Windows, then we don't need the console
+ // anymore.
+ if is_console_virtual {
+ con = None;
+ }
let stream = LossyStandardStream::new(IoStandardStream::new(sty))
.is_console(con.is_some());
BufferWriter {
@@ -623,7 +634,7 @@ impl BufferWriter {
printed: AtomicBool::new(false),
separator: None,
color_choice: choice,
- console: con,
+ console: con.map(Mutex::new),
}
}