stdlib i kolorowe wyjście w C

125

Tworzę prostą aplikację, która wymaga kolorowego wydruku. Jak mogę sprawić, by moje wyjście było kolorowe, tak jak robią to emacs i bash?

Nie obchodzi mnie Windows, ponieważ moja aplikacja jest przeznaczona tylko dla systemów UNIX.

mdml
źródło

Odpowiedzi:

288

Wszystkie nowoczesne emulatory terminali używają kodów ucieczki ANSI, aby pokazać kolory i inne rzeczy.
Nie przejmuj się bibliotekami, kod jest naprawdę prosty.

Więcej informacji tutaj .

Przykład w C:

#include <stdio.h>

#define ANSI_COLOR_RED     "\x1b[31m"
#define ANSI_COLOR_GREEN   "\x1b[32m"
#define ANSI_COLOR_YELLOW  "\x1b[33m"
#define ANSI_COLOR_BLUE    "\x1b[34m"
#define ANSI_COLOR_MAGENTA "\x1b[35m"
#define ANSI_COLOR_CYAN    "\x1b[36m"
#define ANSI_COLOR_RESET   "\x1b[0m"

int main (int argc, char const *argv[]) {

  printf(ANSI_COLOR_RED     "This text is RED!"     ANSI_COLOR_RESET "\n");
  printf(ANSI_COLOR_GREEN   "This text is GREEN!"   ANSI_COLOR_RESET "\n");
  printf(ANSI_COLOR_YELLOW  "This text is YELLOW!"  ANSI_COLOR_RESET "\n");
  printf(ANSI_COLOR_BLUE    "This text is BLUE!"    ANSI_COLOR_RESET "\n");
  printf(ANSI_COLOR_MAGENTA "This text is MAGENTA!" ANSI_COLOR_RESET "\n");
  printf(ANSI_COLOR_CYAN    "This text is CYAN!"    ANSI_COLOR_RESET "\n");

  return 0;
}
Andrejs Cainikovs
źródło
1
Ale przypuszczam, że mogę uruchomić bash w emulacji terminala, która nie obsługuje sekwencji ucieczki ANSI.
ShinTakezou,
Niezła flaga :) Tylko głupota, że ​​pytanie jest oznaczone jako „c”, a nie „c ++”
Stephen
@ShinTakezou: Tak .. W tym przypadku wszystkie kody ucieczki ANSI zostaną zignorowane i nie będziesz mieć opcji, aby utworzyć fantazyjne wyjście.
Andrejs Cainikovs
14
Sekwencje specjalne ANSI nie są interpretowane przez powłoki, są one interpretowane przez emulatory terminala.
ninjalj
6
Szczególnie podobało mi się „nie przejmuj się bibliotekami”! Kody ANSI działają nawet w wierszu poleceń systemu Windows.
SzG
15

Radzenie sobie z sekwencjami kolorów może być skomplikowane, a różne systemy mogą używać różnych wskaźników sekwencji kolorów.

Sugerowałbym, abyś spróbował użyć ncurses . Poza kolorami, ncurses może robić wiele innych fajnych rzeczy z interfejsem konsoli.


źródło
Czy używanie różnych sekwencji kolorów jest powodem, dla którego nie mogę znaleźć pliku „colors.h” z całą wykonaną dla mnie pracą?
Cool Javelin
10

Możesz wyprowadzić specjalne kody kontroli kolorów, aby uzyskać kolorowy wynik terminala. Oto dobre źródło informacji na temat drukowania kolorów .

Na przykład:

printf("\033[22;34mHello, world!\033[0m");  // shows a blue hello world

EDYCJA: Mój oryginalny używał kodów kolorów podpowiedzi, które nie działają :( Ten działa (testowałem to).

Stephen
źródło
edition.c: In function ‘int main(int, const char**)’: edition.c:4: error: unknown escape sequence '\]' edition.c:4: error: unknown escape sequence '\]' edition.c edition.c~Nic więcej niż kilka błędów kompilacji :(
Ponadto moja aplikacja nie powinna być zależna od BASH.
@Koning: To nie jest zależne od BASH, działa też w innych powłokach (ale na pewno nie wszystkie). Zweryfikowałem w ksh i csh. Uwaga: Edytowałem kod sterujący, aby działał poprawnie.
Stephen,
2
Nie będzie. Zależy to od emulacji terminala. Jeśli ANSI rozumie sekwencje ucieczki ANSI, będziesz mieć swoje kolory, pogrubienie lub cokolwiek innego.
ShinTakezou
@Stephen Bonus: Zmień 22, 1aby zobaczyć to pogrubioną czcionką .
xxx ---
9

Możesz przypisać jeden kolor do każdej funkcji, aby była bardziej użyteczna.

#define Color_Red "\33[0:31m\\]" // Color Start
#define Color_end "\33[0m\\]" // To flush out prev settings
#define LOG_RED(X) printf("%s %s %s",Color_Red,X,Color_end)

foo()
{
LOG_RED("This is in Red Color");
}

Podobnie jak mądrze, możesz wybrać różne kody kolorów i uczynić to bardziej ogólnym.

Praveen S
źródło
3

Jeśli używasz tego samego koloru dla całego programu, możesz zdefiniować printf()funkcję.

   #include<stdio.h>
   #define ah_red "\e[31m"
   #define printf(X) printf(ah_red "%s",X);
   #int main()
   {
        printf("Bangladesh");
        printf("\n");
        return 0;
   }
alhelal
źródło
2

Ponieważ nie możesz wydrukować znaku z formatowaniem ciągu. Możesz także pomyśleć o dodaniu formatu z czymś takim

#define PRINTC(c,f,s) printf ("\033[%dm" f "\033[0m", 30 + c, s)

f ma format jak w printf

PRINTC (4, "%s\n", "bar")

wydrukuje blue bar

PRINTC (1, "%d", 'a')

wydrukuje red 97

baz
źródło
2
#include <stdio.h>

#define BLUE(string) "\x1b[34m" string "\x1b[0m"
#define RED(string) "\x1b[31m" string "\x1b[0m"

int main(void)
{
    printf("this is " RED("red") "!\n");

    // a somewhat more complex ...
    printf("this is " BLUE("%s") "!\n","blue");

    return 0;
}

czytanie Wikipedii :

  • \ x1b [0m resetuje wszystkie atrybuty
  • \ x1b [31m ustawia kolor pierwszego planu na czerwony
  • \ x1b [44m ustawi niebieskie tło.
  • oba: \ x1b [31; 44m
  • oba, ale odwrotnie : \ x1b [31; 44; 7m
  • pamiętaj, aby później zresetować \ x1b [0m ...
Ladon
źródło