Просмотр исходного кода

Console color output

Log level and download result string is now colored.
Tatsuhiro Tsujikawa 13 лет назад
Родитель
Сommit
e86fd44dc5
9 измененных файлов с 103 добавлено и 10 удалено
  1. 8 2
      src/BufferedFile.cc
  2. 2 0
      src/BufferedFile.h
  3. 36 4
      src/Logger.cc
  4. 1 0
      src/Logger.h
  5. 1 0
      src/NullOutputFile.h
  6. 2 0
      src/OutputFile.h
  7. 47 4
      src/RequestGroupMan.cc
  8. 5 0
      src/WinConsoleFile.cc
  9. 1 0
      src/WinConsoleFile.h

+ 8 - 2
src/BufferedFile.cc

@@ -54,11 +54,12 @@ BufferedFile::BufferedFile(const char* filename, const char* mode)
 #else // !__MINGW32__
   fp_(a2fopen(filename, mode)),
 #endif // !__MINGW32__
-  open_(fp_)
+  open_(fp_),
+  supportsColor_(isatty(fileno(fp_)))
 {}
 
 BufferedFile::BufferedFile(FILE* fp)
-  : fp_(fp), open_(true)
+  : fp_(fp), open_(true), supportsColor_(isatty(fileno(fp)))
 {}
 
 BufferedFile::~BufferedFile()
@@ -169,4 +170,9 @@ int BufferedFile::flush()
   return fflush(fp_);
 }
 
+bool BufferedFile::supportsColor()
+{
+  return supportsColor_;
+}
+
 } // namespace aria2

+ 2 - 0
src/BufferedFile.h

@@ -77,6 +77,7 @@ public:
   virtual int printf(const char* format, ...);
   // wrapper for fflush
   virtual int flush();
+  virtual bool supportsColor();
   // Mode for reading
   static const char READ[];
   // Mode for writing
@@ -91,6 +92,7 @@ private:
   FILE* fp_;
   // true when file has been opened.
   bool open_;
+  bool supportsColor_;
 };
 
 } // namespace aria2

+ 36 - 4
src/Logger.cc

@@ -34,6 +34,7 @@
 /* copyright --> */
 #include "Logger.h"
 
+#include <unistd.h>
 #include <cstring>
 #include <cstdio>
 
@@ -50,7 +51,14 @@ namespace aria2 {
 
 Logger::Logger()
   : logLevel_(Logger::A2_DEBUG),
-    stdoutField_(0)
+    stdoutField_(0),
+#ifdef __MINGW32__
+    // Windows DOS prompt does not handle ANSI color code, so make
+    // this false.
+    useColor_(false)
+#else // !__MINGW32__
+    useColor_(isatty(STDOUT_FILENO) == 1)
+#endif // !__MINGW32__
 {}
 
 Logger::~Logger()
@@ -131,11 +139,35 @@ void writeHeader
 }
 } // namespace
 
+namespace {
+const char* levelColor(Logger::LEVEL level)
+{
+  switch(level) {
+  case Logger::A2_DEBUG:
+  case Logger::A2_INFO:
+    // We don't print these levels in console
+    return "";
+  case Logger::A2_NOTICE:
+    return "\033[1;32m";
+  case Logger::A2_WARN:
+    return "\033[1;33m";
+  case Logger::A2_ERROR:
+    return "\033[1;31m";
+  default:
+    return "";
+  }
+}
+} // namespace
+
 namespace {
 template<typename Output>
-void writeHeaderConsole(Output& fp, Logger::LEVEL level)
+void writeHeaderConsole(Output& fp, Logger::LEVEL level, bool useColor)
 {
-  fp.printf("[%s] ", levelToString(level));
+  if(useColor) {
+    fp.printf("[%s%s\033[0m] ", levelColor(level), levelToString(level));
+  } else {
+    fp.printf("[%s] ", levelToString(level));
+  }
 }
 } // namespace
 
@@ -164,7 +196,7 @@ void Logger::writeLog
   }
   if(toConsole) {
     global::cout()->printf("\n");
-    writeHeaderConsole(*global::cout(), level);
+    writeHeaderConsole(*global::cout(), level, useColor_);
     global::cout()->printf("%s\n", msg);
     writeStackTrace(*global::cout(), trace);
     global::cout()->flush();

+ 1 - 0
src/Logger.h

@@ -59,6 +59,7 @@ private:
   LEVEL logLevel_;
   SharedHandle<OutputFile> fpp_;
   int stdoutField_;
+  bool useColor_;
   // Don't allow copying
   Logger(const Logger&);
   Logger& operator=(const Logger&);

+ 1 - 0
src/NullOutputFile.h

@@ -45,6 +45,7 @@ public:
   virtual size_t write(const char* str) { return 0; }
   virtual int printf(const char* format, ...) { return 0; }
   virtual int flush() { return 0; }
+  virtual bool supportsColor() { return false; }
 };
 
 } // namespace aria2

+ 2 - 0
src/OutputFile.h

@@ -47,6 +47,8 @@ public:
   virtual size_t write(const char* str) = 0;
   virtual int printf(const char* format, ...) = 0;
   virtual int flush() = 0;
+  // Returns true if the output medium supports ANSI color codes.
+  virtual bool supportsColor() = 0;
 };
 
 } // namespace aria2

+ 47 - 4
src/RequestGroupMan.cc

@@ -716,6 +716,48 @@ RequestGroupMan::DownloadStat RequestGroupMan::getDownloadStat() const
                       lastError);
 }
 
+enum DownloadStatus {
+  A2_STATUS_OK,
+  A2_STATUS_INPR,
+  A2_STATUS_RM,
+  A2_STATUS_ERR
+};
+
+namespace {
+const char* getStatusStr(DownloadStatus status, bool useColor)
+{
+  // status string is formatted in 4 characters wide.
+  switch(status) {
+  case(A2_STATUS_OK):
+    if(useColor) {
+      return "\033[1;32mOK\033[0m  ";
+    } else {
+      return "OK  ";
+    }
+  case(A2_STATUS_INPR):
+    if(useColor) {
+      return "\033[1;34mINPR\033[0m";
+    } else {
+      return "INPR";
+    }
+  case(A2_STATUS_RM):
+    if(useColor) {
+      return "\033[1mRM\033[0m  ";
+    } else {
+      return "RM  ";
+    }
+  case(A2_STATUS_ERR):
+    if(useColor) {
+      return "\033[1;31mERR\033[0m ";
+    } else {
+      return "ERR ";
+    }
+  default:
+    return "";
+  }
+}
+} // namespace
+
 void RequestGroupMan::showDownloadResults(OutputFile& o, bool full) const
 {
 #ifdef __MINGW32__
@@ -739,6 +781,7 @@ void RequestGroupMan::showDownloadResults(OutputFile& o, bool full) const
   }
   std::string line(pathRowSize, '=');
   o.printf("%s\n", line.c_str());
+  bool useColor = o.supportsColor();
   int ok = 0;
   int err = 0;
   int inpr = 0;
@@ -751,16 +794,16 @@ void RequestGroupMan::showDownloadResults(OutputFile& o, bool full) const
     }
     const char* status;
     if((*itr)->result == error_code::FINISHED) {
-      status = "OK";
+      status = getStatusStr(A2_STATUS_OK, useColor);
       ++ok;
     } else if((*itr)->result == error_code::IN_PROGRESS) {
-      status = "INPR";
+      status = getStatusStr(A2_STATUS_INPR, useColor);
       ++inpr;
     } else if((*itr)->result == error_code::REMOVED) {
-      status = "RM";
+      status = getStatusStr(A2_STATUS_RM, useColor);
       ++rm;
     } else {
-      status = "ERR";
+      status = getStatusStr(A2_STATUS_ERR, useColor);
       ++err;
     }
     if(full) {

+ 5 - 0
src/WinConsoleFile.cc

@@ -103,4 +103,9 @@ int WinConsoleFile::flush()
   return 0;
 }
 
+bool WinConsoleFile::supportsColor()
+{
+  return false;
+}
+
 } // namespace aria2

+ 1 - 0
src/WinConsoleFile.h

@@ -47,6 +47,7 @@ public:
   virtual size_t write(const char* str);
   virtual int printf(const char* format, ...);
   virtual int flush();
+  virtual bool supportsColor();
 private:
   DWORD stdHandle_;
   // Don't allow copying