- 터미널 색상 문제는 취향보다 표준 부재와 구현 차이에 가까워, 같은 명령 출력도 터미널·테마·앱 조합에 따라 읽기 어려워질 수 있음
- 기본 16 ANSI 색상, 256색, 24비트 hex 색상이 함께 쓰이지만, 색상 번호가 실제 어떤 색으로 보일지는 터미널 에뮬레이터마다 달라짐
- 파란 글자/검은 배경, 밝은 노란색/흰 배경, Solarized의 회색 매핑,
ngrok배경색처럼 대비 충돌은 프로그램의 가정과 사용자 테마가 어긋날 때 드러남 - 대응책은 팔레트 재설정,
base16-shell,LS_COLORS,NO_COLOR=true,--color=always,unbuffer, Vim/Neovim의 24비트 색상 지원처럼 여러 층으로 나뉨 - iTerm2, tabby, kitty, Ghostty, Windows Terminal의 minimum contrast 기능은 완벽한 해결책은 아니지만, 읽을 수 없는 출력이 생기는 위험을 줄여줌
ANSI 색상과 터미널별 차이
- 터미널에는 보통 검정, 빨강, 초록, 노랑, 파랑, 마젠타, 시안, 흰색과 각각의 밝은 버전으로 구성된 16개 ANSI 색상이 있음
- 프로그램은 ANSI escape code를 출력해 색상을 지정함
- 예를 들어
\033[38;5;{num}m형태로 전경색 번호를 지정할 수 있음
- 예를 들어
- 문제는 ANSI 색상 번호가 실제 어떤 hex 색상에 대응되는지 일관된 표준이 없다는 점임
- 터미널 에뮬레이터마다 색을 직접 선택함
- Wikipedia의 ANSI escape code 색상 표에서도 구현별 차이가 큼
- 이 차이 때문에
ls가 디렉터리에 사용하는 파란색이 검은 배경에서 잘 보이지 않을 수 있음 - 밝은 노란색과 흰 배경 조합도 거의 읽기 어렵고, 밝은 초록색 같은 다른 색상에서도 비슷한 문제가 생길 수 있음
색상 팔레트를 재설정하는 방법
- 기본 ANSI 색상이 마음에 들지 않거나 대비 문제가 있으면 팔레트 재설정으로 대응할 수 있음
-
터미널 에뮬레이터에서 설정
- 현대적인 터미널 에뮬레이터 대부분은 색상을 재설정하는 기능을 제공함
- 일부는 기본 포함 테마를 제공함
- 인기 있는 터미널 에뮬레이터일수록 선택 가능한 테마가 더 많을 수 있음
-
셸 스크립트로 설정
- ANSI escape code를 출력해 터미널 에뮬레이터의 색상 팔레트를 바꿀 수 있음
- base16-shell의 Solarized Light 스크립트는 여러 터미널별 escape code 관례를 사용함
- 스크립트는
TERM환경 변수에 따라 적절한 escape code 스타일을 고르려 함 - 셸 스크립트 방식은 터미널 에뮬레이터를 바꿔도 같은 색상 설정을 유지하기 쉬움
- 다만 모든 터미널 에뮬레이터가 이 방식의 팔레트 변경을 지원하지는 않으며, 지원하더라도 결과가 조금씩 다를 수 있음
256색, 24비트 색상, 도구별 테마
- 많은 터미널은 색상 지정 방식을 3가지로 지원함
- 16 ANSI 색상
- 확장 256색
#ffea03같은 24비트 hex 색상
fd는 출력에서^[[38;5;48m같은 escape code를 사용해 전경색 48번을 지정함- 이 색은 일반 터미널 색상표에 없는 라임색처럼 보일 수 있음
- 사용 중인 색상표와 대비가 나쁠 수 있음
bat도 비슷하게 색상을 사용하지만, 다양한 터미널 테마에서 동작하려는 기본 출력으로 보임fd,bat,delta같은 일부 최신 터미널 도구는 임의의 사용자 지정 테마를 지원함- 기본 테마가 터미널 배경과 충돌할 수 있음
- 대신 16 ANSI 색상만 고르는 것보다 도구 출력의 테마를 더 세밀하게 제어할 수 있음
bat --theme ansi를 쓰면bat가 일반 터미널 색상표에 설정된 ANSI 색상을 사용함
Solarized와 base16에서 생기는 충돌
- Solarized Light는 구현에 따라 bright 색상 매핑이 다르게 보일 수 있음
- iTerm의 기본 Solarized Light 테마는 원래 Solarized 디자인처럼 색상 9~14번, 즉 “bright blue”, “bright red” 등을 회색 계열에 매핑함
ls가 디렉터리와 실행 파일에 bright 색상을 쓰면 회색으로 보일 수 있음
- base16 Solarized Light는 bright 색상을 회색이 아니라 실제 색상으로 유지하는 변형으로 사용될 수 있음
- 이 차이는 Vim Solarized 색상표가 회색을 사용할 수 있도록 원래 Solarized가 설계된 결과로 보임
base16-shell은base16-vim에 추가 색상을 제공하려고 색상 16~21을 설정함ngrok이 배경을 색상 16번 “black”으로 설정하려 할 때, 해당 색상이 밝은 주황색으로 재매핑되어 있으면 매우 이상한 배경이 생김- 프로그램이 ANSI 배경색을 지정하고 사용자가 그 색을 다른 의미로 재매핑하면 이런 충돌이 생기기 쉬움
minimum contrast로 대비 문제 줄이기
- 일부 터미널은 minimum contrast 기능으로 전경색과 배경색의 대비가 충분하지 않을 때 색상을 자동 조정함
- iTerm2, tabby, kitty의 text_fg_override_threshold, Ghostty, Windows Terminal이 이 기능을 제공함
- iTerm에서 minimum contrast 값을 40으로 설정하면,
ngrok배경색 충돌처럼 읽기 어려운 출력도 더 읽기 쉬워짐 - 색상 설정이 잘못되었거나 프로그램과 테마가 충돌했을 때, minimum contrast는 우발적인 가독성 문제를 줄이는 실용적인 안전장치임
TERM, 파이프, 색상 비활성화
- SSH로 접속한 시스템이 로컬의
TERM환경 변수 값을 지원하지 않으면 색상이 제대로 동작하지 않을 수 있음 - 시스템은
terminfo데이터베이스를 사용하며,TERM값이 해당 데이터베이스에 없으면 터미널에 맞는 색상 출력을 알기 어려움 - 재현 가능한 환경은 없었지만, Stack Overflow 답변은
ssh대신TERM=xterm ssh같은 형태를 제안함 - 명령어를 파이프로 연결하면 색상이 비활성화되는 경우가 있음
fd | less는 색상 없이 출력될 수 있음- 일반적으로
grep같은 도구에 넘길 때 escape code 없이 평문만 나오는 것은 유용함
- 색상을 유지하고 싶으면
unbuffer fd | less -r을 사용할 수 있음unbuffer는 명령이 TTY에 쓰고 있다고 인식하도록 tty를 열어줌- 파이프에 쓸 때 프로그램 출력이 버퍼링되는 문제도 해결함
- 일부 명령어는
fd처럼--color=always플래그로 항상 색상을 출력할 수 있음
ls 색상을 끄거나 바꾸기
- 일부 사용자는
ls색상 출력을 원하지 않음- 파란색이 검은 배경에서 읽기 어렵거나
- 터미널 색상표를 조정하고 싶지 않거나
- 색상 자체가 도움이 되지 않을 수 있음
- 선택지는 여러 가지임
ls --color=never로 색상을 끌 수 있음LS_COLORS환경 변수로ls가 쓰는 색상을 사용자 지정할 수 있음- 일부 프로그램은
NO_COLOR=true를 지원하며, no-color.org에 목록이 있음
- 예시로
LS_COLORS="fi=0:di=0:ln=0:pi=0:so=0:bd=0:cd=0:or=0:ex=0" ls처럼 설정하면 여러 파일 종류의 색상 스타일을 0으로 맞출 수 있음
Vim과 Neovim의 변화
- Vim 색상 설정은 과거에 터미널 색상표와 Vim 색상표를 맞춰야 해서 문제가 많았음
- 터미널 안의 Vim 색상표 설정 방식은 크게 2가지임
- Vim 색상 클래스를 ANSI 색상 번호에 매핑함
- 색상표가
#faea99같은 24비트 hex 색상을 직접 사용함
- 20년 전에는 24비트 hex 색상을 지원하는 터미널이 흔하지 않았고, Vim도 터미널에서 24비트 색상 사용을 지원하지 않았음
- Vim은 2016년에 24비트 색상 지원을 추가함
- Neovim 0.10은 2024년 5월 릴리스되었고, 24비트 색상 지원 터미널에서는
termguicolors가 기본으로 켜짐 - 2024년에 24비트 색상을 지원하지 않는 터미널을 쓸 계획이 없다면, 터미널 색상표와 Vim 색상표를 반드시 동기화해야 하는 부담은 사라짐
- 이 변화로
base16-shell이 Vim 연동을 위해 색상 16~21을 특수하게 설정할 필요가 줄어듦- 해당 부분을 제거하면
ngrok의 주황색 배경 같은 충돌을 피할 수 있음
- 해당 부분을 제거하면
base16 사용 경험과 한계
- base16-shell과 base16-vim을 함께 쓰면 터미널과 Vim 색상을 맞추기 쉬움
- fish 설정에 몇 줄을 추가하고
.vimrc에 몇 줄을 넣는 방식으로 설정할 수 있음 - base16은 모두에게 맞는 방식은 아님
- 내장 테마 수가 제한적이고 마음에 드는 테마가 없을 수 있음
- Solarized base16 테마는 bright ANSI 색상을 일반 색상과 같게 설정하며, bright 색상이 달라야 하는 사용 사례에는 문제가 될 수 있음
base16-vim에 더 많은 색상을 제공하려고 색상 16~21을 설정하는 방식은 24비트 색상 지원 터미널만 쓰는 환경에서는 필요 없을 수 있음- 색상 16~21 설정은 Linux framebuffer terminal처럼 256색을 지원하지 않는 터미널에서 문제가 될 수 있음
- base16의 커뮤니티 포크로 tinted-theming이 있음
색상표 도구와 인기 테마
- rootloops.sh는 색상표 생성을 위한 도구임
- 함께 참고할 글로 “let’s create a terminal color scheme”가 있음
- Mastodon 응답에서 언급된 인기 색상표는 다음과 같음
여전히 남는 문제
tmux, SSH, Vim 조합처럼 여러 프로그램이 만나는 지점에는 추가적인 색상 문제가 생길 수 있음- 좋은 색상표를 고르는 일 자체도 어려움
- 색각 이상이 있는 사용자는 적절한 색상표를 찾기 어려울 수 있음
- 배경색이 커서나 선택 영역 색상과 너무 가까우면 위치를 찾기 어려움
- 모든 프로그램에서 잘 동작하는 색상을 찾기는 어렵고,
ngrok사례처럼 충돌이 생길 수 있음
- Nethack이나 Midnight Commander처럼 기본 ANSI 색상 기반의 특정한 “클래식” 모습을 기대하는 프로그램은 Solarized 같은 테마에서 낯설게 보일 수 있음
- 한 가지 대응법은 프로그램 실행 직전에 ANSI 팔레트를 바꾸는 것임
- 예를 들어 Nethack 실행 전에 노란색을 더 밝은 노란색으로 재매핑할 수 있음
- 색상이 그냥 잘 동작하길 원하는 사용자에게는 많은 수동 설정이 부담이며, 합리적인 기본값과 minimum contrast 같은 기능이 중요함