처리중입니다. 잠시만 기다려주세요.
TTJ 코딩클래스
정규반 단과 자료실 테크 뉴스 코딩 퀴즈
테크 뉴스
Hacker News 2026.06.16 60

이미지를 반반 섞었는데 왜 더 어두워질까? 코더라면 꼭 알아야 할 감마 보정

Hacker News 원문 보기

이미지를 절반씩 섞었는데, 왜 더 칙칙해질까요?

혹시 이런 경험 해보신 적 있으세요? 빨간색과 초록색을 50%씩 섞었더니 생각보다 어둡고 탁한 색이 나오거나, 반투명 PNG를 배경 위에 올렸는데 경계선이 거뭇하게 떠 보이는 경우요. 아니면 이미지를 절반 크기로 줄였더니 원본보다 묘하게 어두워 보이기도 하고요. 이게 다 우연이 아니라, 감마(gamma) 라는 개념을 모른 채로 픽셀 값을 그대로 더하고 빼서 생기는 일이거든요.

색을 다루는 코드를 한 번이라도 짜본 사람이라면 꼭 짚고 넘어가야 하는 주제인데, 의외로 모르고 지나가는 분이 정말 많아요. 오늘은 이 감마라는 녀석이 도대체 뭔지, 왜 신경 써야 하는지 커피 한 잔 마시면서 듣는 느낌으로 풀어볼게요.

사람 눈은 밝기를 '있는 그대로' 느끼지 않아요

핵심부터 말하면, 우리 눈은 빛의 밝기를 물리적인 양 그대로 받아들이지 않아요. 어두운 영역의 미세한 차이에는 굉장히 예민하고, 밝은 영역의 차이에는 둔감하거든요. 캄캄한 방에서 촛불 하나 켜면 확 밝아진 게 느껴지지만, 환한 대낮에 형광등 하나 더 켜도 별 차이를 못 느끼는 것과 같아요.

그래서 이미지를 저장할 때 영리한 트릭을 써요. 0~255 사이의 한정된 숫자를 어두운 쪽에 더 촘촘하게 배분하는 거죠. 이걸 감마 인코딩이라고 부르고, 우리가 흔히 쓰는 PNG·JPG 이미지는 거의 다 'sRGB'라는 표준에 따라 이렇게 인코딩되어 저장돼 있어요. 즉, 파일 안의 픽셀 값 128물리적인 빛의 절반이 아니에요. 실제로는 빛의 약 21% 정도밖에 안 되는 밝기예요. 사람 눈에 '중간 회색'으로 보이도록 일부러 비틀어 놓은 값이거든요.

인코딩된 값으로 계산하면 왜 틀릴까

문제는 여기서 시작돼요. 우리가 코드에서 (a + b) / 2 같은 평균을 내거나, 블러를 먹이거나, 이미지를 리사이즈할 때 하는 계산은 빛의 양을 더하는 물리 연산이에요. 그런데 막상 우리가 가진 픽셀 값은 빛의 양이 아니라 '눈에 보이는 밝기로 비틀어진 값'이잖아요.

비유하자면, 데시벨(dB)로 표시된 두 소리의 크기를 그냥 숫자로 더하는 거랑 똑같아요. 로그 스케일 값을 산술적으로 더하면 엉뚱한 결과가 나오죠. 마찬가지로 sRGB 값 188(흰색에 가까움)과 0(검정)의 평균을 내면 94가 나오는데, 이건 실제 빛의 절반보다 한참 어두운 값이라 결과물이 칙칙해 보이는 거예요.

올바른 방법은 이래요.

1. 픽셀 값을 먼저 선형(linear) 공간으로 되돌려요. (대략 값을 2.2 제곱 해주는 디코딩)
2. 이 진짜 빛의 양으로 더하기·평균·블렌딩을 해요.
3. 결과를 다시 sRGB로 인코딩해서 화면에 뿌려요. (대략 1/2.2 제곱)

참고로 sRGB의 변환 곡선은 정확히 2.2 거듭제곱은 아니고, 아주 어두운 영역에는 직선 구간이 따로 붙어 있어요. 0 근처에서 미분값이 무한대로 튀는 걸 막으려는 장치죠. 그래서 정밀하게 하려면 단순 거듭제곱이 아니라 표준 sRGB 변환식을 써야 해요.

게임 엔진과 그래픽 업계는 이미 다 이렇게 해요

사실 이건 새로운 발견이 아니에요. 언리얼이나 유니티 같은 게임 엔진은 조명 계산을 전부 선형 공간에서 처리하고 마지막에 화면용으로 인코딩(감마 보정)해서 내보내요. 텍스처를 불러올 때 'sRGB 텍스처'로 표시하는 옵션이 바로 'GPU야, 이건 인코딩된 값이니 쓰기 전에 선형으로 풀어서 써'라는 신호고요. 알베도(색) 텍스처는 sRGB로, 노멀맵이나 러프니스 같은 데이터 텍스처는 선형으로 읽는 이유도 여기에 있어요. 데이터값은 애초에 빛이 아니니까요.

반대로 웹 캔버스(<canvas>)나 옛날 이미지 라이브러리들은 기본적으로 인코딩된 값 위에서 그냥 연산하는 경우가 많았어요. 그래서 같은 알파 블렌딩을 해도 결과가 미묘하게 다르게 나오곤 했죠.

한국 개발자에게: 언제 이게 발목을 잡을까

프론트엔드에서 캔버스로 이미지 필터를 만들거나, 백엔드에서 썸네일을 대량 생성하거나, 셰이더로 그라데이션을 그리는 분이라면 이건 남 얘기가 아니에요. 특히 반투명 합성리사이즈에서 티가 확 나요. 흰 글자에 그림자를 깔거나 안티앨리어싱된 글자를 어두운 배경에 올렸을 때 가장자리가 지저분해 보인다면 십중팔구 감마를 무시한 블렌딩 때문이거든요.

당장 모든 코드를 뜯어고칠 필요는 없지만, '색을 평균 내거나 섞는 연산을 한다면 선형 공간으로 바꾸고 해야 정확하다'는 사실 하나만 머릿속에 박아두면, 나중에 디자이너가 "이거 색이 좀 죽었는데요?" 할 때 원인을 바로 짚을 수 있어요. ImageMagick에는 -colorspace RGB로 선형 변환하는 옵션이 있고, 대부분의 그래픽 API에도 sRGB 변환 함수가 마련돼 있으니 찾아 쓰면 돼요.

마무리

핵심 한 줄: 우리가 가진 픽셀 값은 '빛의 양'이 아니라 '사람 눈에 맞게 비튼 값'이라, 더하고 섞는 계산을 하려면 일단 선형으로 풀었다가 다시 비틀어야 한다는 것!

여러분이 짠 코드 중에 이미지 블렌딩이나 리사이즈가 들어간 곳, 혹시 감마를 무시하고 있진 않았나요? 화면을 다시 한번 들여다보면 의외의 칙칙함을 발견할지도 몰라요.


🔗 출처: Hacker News

이 뉴스가 유용했나요?

TTJ 코딩클래스 정규반

월급 외 수입,
코딩으로 만들 수 있습니다

17가지 수익 모델을 직접 실습하고, 1,300만원 상당의 자동화 도구와 소스코드를 받아가세요.

144+실전 강의
17개수익 모델
4.9수강생 평점
정규반 자세히 보기

"비전공 직장인인데 반년 만에 수익 파이프라인을 여러 개 만들었습니다"

실제 수강생 후기
  • 비전공자도 6개월이면 첫 수익
  • 20년 경력 개발자 직강
  • 자동화 프로그램 + 소스코드 제공

매일 AI·개발 뉴스를 받아보세요

주요 테크 뉴스를 매일 아침 이메일로 전해드립니다.

스팸 없이, 언제든 구독 취소 가능합니다.