![[Develop] svg vs png : 뭐가 더 좋을까?](https://img1.daumcdn.net/thumb/R750x0/?scode=mtistory2&fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F2h5jr%2FbtsMaQxCRTP%2FHbaLC0oEJ4M809bhyGzmK1%2Fimg.png)
개요
Flutter뿐만 아니라 프런트엔드 개발을 하다 보면 앱 내부에 이미지를 넣어야 할 때가 있다. 이런 상황에서 일반적으로 두 가지의 포맷을 사용하곤 하는데, 그 두 포맷이 svg와 png다. (jpeg는 투명도가 없기에 사용하지 않는다.)
figma를 보고 작업을 하다보면 디자이너가 아이콘들을 svg 포맷으로 주곤 한다. 평소에는 별생각 없이 svg 파일을 받아 사용했는데 문득 의문이 들었다. 'svg를 주로 사용하는 이유가 뭐지?', 'png도 같은 역할을 하는데, 둘의 명확한 차이에 대해 나는 알고 있었나?'.
그래서 개발에서 둘의 차이에 대해 조금 더 깊게 알아보기로 했다. 우선은 간단하게 각각의 특징에 대해 알아보고 성능 상의 차이에 대해 알아보자.
각각의 특징
SVG 포맷
SVG는 Scalable Vector Graphics의 약자로, 벡터 그래픽을 위한 XML 기반의 이미지 형식이다. 픽셀 단위로 저장하는 래스터 이미지(PNG, JPEG)와 달리, 수학적 좌표와 도형 정보로 그래픽을 표현하기 때문에 크기를 조정해도 품질이 유지된다.
조금 더 쉽게 이야기하자면, SVG는 사각형, 선, 타원 등 기본 도형들을 조합하여 구성되며 정확한 좌표들의 집합이 아닌 화면에 무엇을 그릴지에 대한 명령어 집합이므로, 크기를 조정해도 품질이 유지된다.
SVG의 특징으로는 아래의 것들이 있다.
- 무한 확장 가능: 명령어 집합이므로 크기를 무한대로 확장해도 화질 저하가 일어나지 않는다.
- 작은 파일 크기: 복잡한 이미지라도 PNG/JPEG보다 용량이 적을 수 있다.
- 텍스트 편집 가능: 이미지 내 텍스트를 직접 수정할 수 있다.
- 검색엔진(SEO) 친화적: XML 기반이므로 검색엔진이 내용을 읽을 수 있다.
- 복잡한 이미지에는 부적합: 사진 같은 이미지 표현은 어렵다.
- 렌더링 성능 문제: 도형이 많아지면 브라우저에서 렌더링 속도가 느려질 수 있다.
PNG 포맷
PNG는 Portable Network Graphics의 약자로, 손실 없는 압축 방식(Lossless Compression)을 사용하는 래스터 이미지 파일 형식이다. 투명도(Alpha Channel)를 지원하며, 다양한 색상을 표현할 수 있어 웹 및 디자인 작업에서 널리 사용된다.
래스터 방식?
픽셀(pixel) 단위의 데이터를 저장하는 방식을 말한다. 이미지가 정해진 해상도로 저장되며, 확대하거나 축소할 경우 품질 저하가 일어날 수 있다.
PNG의 특징으로는 아래의 것들이 있다.
- 손실 없는 압축(Lossless Compression): 저장할 때 이미지의 품질이 유지된다.
- 투명도(Alpha Channel) 지원: 배경을 투명하게 설정할 수 있다. (JPEG는 투명도를 지원하지 않는다.)
- 색상 표현력 높음: 최대 16비트(65,536색)까지 지원하는 버전이 존재한다.
- 큰 파일 크기: JPEG보다 크기가 커서 웹에서 사용 시 로딩 속도가 느려질 수 있다.
- 애니메이션 미지원: GIF처럼 여러 프레임을 담아 움직이는 기능이 없다. (APNG는 예외)
- 낮은 사진 압축률: 사진 저장 시 JPEG보다 효율이 떨어진다.
SVG vs PNG: 개발에서의 성능 차이
SVG의 렌더링 과정
SVG는 XML 기반의 벡터 이미지로, 그래픽 엔진이 이를 해석하여 화면에 표시하기 위해 여러 단계를 거쳐야 한다.
- 파일 파싱(XML 해석): SVG는 XML 형식이므로, 그래픽 엔진이 파일을 불러오면 먼저 이를 해석해야 한다.
- 도형 계산: SVG 내부의 각 도형(path, circle, rect 등)에 대한 좌표와 스타일을 계산한다.
- 벡터 -> 픽셀 변환: 벡터 데이터를 픽셀 단위로 변환하여 화면에 표시한다.
- 렌더링 적용: 변환된 픽셀 데이터를 브라우저 화면에 렌더링한다.
이 과정에서 복잡한 벡터 이미지는 연산 비용이 증가할 수 있으며, 특히 브라우저가 실시간으로 SVG를 조작하거나 애니메이션을 적용할 경우 성능 저하가 발생할 가능성이 있다.
PNG의 렌더링 과정
PNG는 래스터 이미지(비트맵)로, 이미 픽셀 단위로 저장된 상태에서 로드된다.
- 파일 로드: PNG 파일을 서버 혹은 로컬에서 가져온다.
- 압축 해제: PNG는 손실 없는 압축을 사용하므로, 그래픽 엔진이 이를 해제하는 과정이 필요하다.
- 화면에 출력: 압축 해제된 픽셀 데이터를 그대로 화면에 배치한다.
SVG와 달리 PNG는 렌더링 과정에서 추가적인 계산이 거의 필요하지 않으므로 속도가 빠르다. 즉, SVG는 벡터를 픽셀로 변환하는 추가적인 과정이 있는 반면, PNG는 저장된 픽셀 데이터를 바로 불러와 표시하기 때문에 렌더링 성능에서 유리하다.
성능 비교: SVG vs PNG
파일 크기 | 단순한 도형은 작지만, 복잡한 것은 크다. | 이미지 크기에 따라 다름, 일반적으로 크다 |
확대/축소 품질 | 무한 확장 가능 (벡터 기반) | 확대 시 품질 저하 (픽셀 기반) |
렌더링 속도 | 복잡한 도형일수록 느리다. | 빠르다. |
애니메이션 | CSS 및 JavaScript로 가능하다. | 지원되지 않는다. |
SEO 친화성 | 검색 엔진이 읽을 수 있다. | 검색 엔진이 내용을 해석할 수 없다. |
시뮬레이터의 결과로는 아래와 같이 나온다. 꽤 차이가 많이 나는 것 같은데, 꽤 과장된 결과이며 실제로는 엄청나게 미미한 차이가 난다. ▼
결론: 그러면 뭐가 더 적합할까?
위의 상당히 정석적인 특징 정리로는 PNG가 로딩 성능이 더 빠르기에 성능상으로는 PNG가 더 좋다는 것을 알 수 있다.
"그럼 결론이 났네? PNG를 써야지"
하지만 렌더링 속도가 빠르다고 무조건 더 우월한 것은 아니다. 심지어 복잡도가 30이하인 SVG 파일들은 렌더링을 하는데 1~10ms 이내에 렌더링이 된다. 개발에 사용되는 일반적인 SVG 파일들은 PNG와 렌더링 속도에서 큰 차이가 나지 않는다.
"그럼 결론이 뭔데?"
두 가지 결론이 있다. 첫번째 결론은 조금은 뻔한 결론으로 SVG와 PNG는 각각의 장점과 단점이 있으며, 사용하는 환경과 목적에 따라 적절한 포맷을 선택하는 것이 중요하다는 것이다. 두번째 결론은 둘 중 용량이 더 작은게 성능상으로 더 좋다는 것이다.
렌더링에 있어서 SVG가 조금 더 느리다고는 하지만, 일반적으로 우리가 사용하는 SVG들의 복잡도는 30을 넘지 않는다. 로고의 경우에는 100이 넘어갈 수 있지만, 로고를 앱이나 웹의 모든 페이지에서 사용하는 것이 아니기에 이를 큰 요소로 잡기는 어렵다. 이런 경우 단순 렌더링 성능보다 파일을 불러오는 속도가 더 중요해진다. 즉, 더 적은 용량이 더 효율적이라는 결론이다. ▼
물론 그 외의 요소들도 잘 따져가며 사용해야한다. 앞에서 언급된 반응형이나 애니메이션 여부 등등도 꽤나 중요한 요인이 될 수 있다. 이런 요인들을 잘 따져가며 선택을 하면 더 좋은 성능의 웹/앱이 개발될 수 있을 것이라고 생각한다. 물론 그래도 일반적인 경우엔 용량부터 생각하는게 좋을거 같다.