2016-02-02 10:04:50 -08:00
// Copyright (c) .NET Foundation and contributors. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
using System ;
using System.IO ;
namespace Microsoft.DotNet.Cli.Build.Framework
{
public class AnsiConsole
{
2016-02-23 12:10:50 -08:00
private AnsiConsole ( TextWriter writer )
2016-02-02 10:04:50 -08:00
{
Writer = writer ;
2016-02-24 10:51:36 -08:00
2016-02-23 12:10:50 -08:00
OriginalForegroundColor = Console . ForegroundColor ;
2016-02-02 10:04:50 -08:00
}
2016-02-24 10:51:36 -08:00
2016-02-02 10:04:50 -08:00
private int _boldRecursion ;
2016-02-24 10:51:36 -08:00
2016-02-23 12:10:50 -08:00
public static AnsiConsole GetOutput ( )
2016-02-02 10:04:50 -08:00
{
2016-02-23 12:10:50 -08:00
return new AnsiConsole ( Console . Out ) ;
2016-02-02 10:04:50 -08:00
}
2016-02-24 10:51:36 -08:00
2016-02-23 12:10:50 -08:00
public static AnsiConsole GetError ( )
2016-02-02 10:04:50 -08:00
{
2016-02-23 12:10:50 -08:00
return new AnsiConsole ( Console . Error ) ;
2016-02-02 10:04:50 -08:00
}
2016-02-24 10:51:36 -08:00
2016-02-02 10:04:50 -08:00
public TextWriter Writer { get ; }
2016-02-24 10:51:36 -08:00
2016-02-02 10:04:50 -08:00
public ConsoleColor OriginalForegroundColor { get ; }
2016-02-24 10:51:36 -08:00
2016-02-02 10:04:50 -08:00
private void SetColor ( ConsoleColor color )
{
2016-02-24 10:51:36 -08:00
const int Light = 0x08 ;
int c = ( int ) color ;
2016-02-02 10:04:50 -08:00
2016-02-24 10:51:36 -08:00
Console . ForegroundColor =
c < 0 ? color : // unknown, just use it
_boldRecursion > 0 ? ( ConsoleColor ) ( c & ~ Light ) : // ensure color is dark
( ConsoleColor ) ( c | Light ) ; // ensure color is light
}
2016-02-02 10:04:50 -08:00
private void SetBold ( bool bold )
{
_boldRecursion + = bold ? 1 : - 1 ;
if ( _boldRecursion > 1 | | ( _boldRecursion = = 1 & & ! bold ) )
{
return ;
}
2016-02-24 10:51:36 -08:00
// switches on _boldRecursion to handle boldness
SetColor ( Console . ForegroundColor ) ;
2016-02-02 10:04:50 -08:00
}
public void WriteLine ( string message )
2016-02-24 10:51:36 -08:00
{
Write ( message ) ;
Writer . WriteLine ( ) ;
}
public void Write ( string message )
2016-02-02 10:04:50 -08:00
{
var escapeScan = 0 ;
for ( ; ; )
{
var escapeIndex = message . IndexOf ( "\x1b[" , escapeScan ) ;
if ( escapeIndex = = - 1 )
{
var text = message . Substring ( escapeScan ) ;
Writer . Write ( text ) ;
break ;
}
else
{
var startIndex = escapeIndex + 2 ;
var endIndex = startIndex ;
while ( endIndex ! = message . Length & &
message [ endIndex ] > = 0x20 & &
message [ endIndex ] < = 0x3f )
{
endIndex + = 1 ;
}
2016-02-24 10:51:36 -08:00
2016-02-02 10:04:50 -08:00
var text = message . Substring ( escapeScan , escapeIndex - escapeScan ) ;
Writer . Write ( text ) ;
if ( endIndex = = message . Length )
{
break ;
}
2016-02-24 10:51:36 -08:00
2016-02-02 10:04:50 -08:00
switch ( message [ endIndex ] )
{
case 'm' :
int value ;
if ( int . TryParse ( message . Substring ( startIndex , endIndex - startIndex ) , out value ) )
{
switch ( value )
{
case 1 :
SetBold ( true ) ;
break ;
case 22 :
SetBold ( false ) ;
break ;
case 30 :
SetColor ( ConsoleColor . Black ) ;
break ;
case 31 :
SetColor ( ConsoleColor . Red ) ;
break ;
case 32 :
SetColor ( ConsoleColor . Green ) ;
break ;
case 33 :
SetColor ( ConsoleColor . Yellow ) ;
break ;
case 34 :
SetColor ( ConsoleColor . Blue ) ;
break ;
case 35 :
SetColor ( ConsoleColor . Magenta ) ;
break ;
case 36 :
SetColor ( ConsoleColor . Cyan ) ;
break ;
case 37 :
SetColor ( ConsoleColor . Gray ) ;
break ;
case 39 :
SetColor ( OriginalForegroundColor ) ;
break ;
}
}
break ;
}
2016-02-24 10:51:36 -08:00
2016-02-02 10:04:50 -08:00
escapeScan = endIndex + 1 ;
}
}
}
}
}