데일리호텔(DAILYHOTEL) 안드로이드 앱 SVG 아이콘 적용기
이 글에서는 데일리호텔이 왜 png에서 svg로 갈아탔는지, 그리고 간단한 svg 실무 적용 팁에 대해 알려드리고자 합니다.
SVG는 “ Scalable Vector Graphics”의 약자입니다.
JPEG, PNG 처럼 SVG도 그래픽 포맷(Graphic format) 중 하나입니다. SVG는 벡터 기반이기 때문에 리사이징이 되어도 전혀 깨지지 않습니다. 모든 해상도에서 자유자재로 활용할 수 있기 때문에 특정 해상도에 제한되어있지 않다는 게 핵심 포인트라고 할 수 있습니다.
다른 그래픽 포맷보다 SVG가 좋은 이유는 참으로도 다양합니다. 필자가 생각했을 때의 핵심 장점들은 이러합니다.
1. 특정 사이즈에 구애를 받지 않습니다.
즉 어느 해상도에서든 pixelate 되지 않습니다. 요새 디자이너들이 자주 사용하는 디자인 프로그램인 스케치로 따지면 아트보드와 비슷한 것 같습니다. 아트보드 안에 만든 레이어, 요소들은 다 벡터 기반입니다. 아트보드를 리사이징 해도 안에 요소들은 깨지지 않고 그 모습 그대로를 가지고 있습니다. 같은 원리로 SVG도 어떤 사이즈로든 그 모습 그대로가 유지됩니다. 그렇기 때문에 사이즈별로 아이콘을 일일이 생성해서 개발자에게 넘겨줄 필요가 없습니다. SVG 파일 하나면 모든 해상도를 대응할 수 있습니다.
2. 작은 파일 사이즈
비트맵 이미지들(PNG, JPEG) 같은 경우 파일 크기를 결정하는 주요 요소는 바로 ‘해상도’입니다. 예를 들어 5000x5000 픽셀 이미지는 항상 500x500보다 파일 사이즈가 큽니다.
반면, SVG 그래픽 같은 경우 파일 크기를 결정하는 주요 요소는 바로 ‘복잡도’입니다. Path가 비교적 적은 간단한 이미지는 PNG, JPEG 보다 파일 사이즈가 적을 수도 있지만 이미지를 구성하는 요소의 복잡도(레이어가 많다든지 특정 효과가 많다든지)에 따라 파일 사이즈가 커집니다.
하지만 이런 용량 문제는 SVG Optimizing을 하게 되면 나름 해결됩니다. 필자 같은 경우 업무적으로 스케치를 사용하고 있기 때문에 스케치에서 제공해주는 SVGO Compressor 플러그인을 활용하고 있습니다.
https://github.com/BohemianCoding/svgo-compressor
작은 파일 사이즈로 인해 로딩 시간도 훨씬 더 줄어든다는 장점 또한 있습니다.
여기서 잠깐!
혹시나 Bitmap과 SVG의 구성요소에 대해 잘 모르실 분들을 위하여 간단한 비교 해드리겠습니다.
비트맵 그래픽: Raster Graphics (픽셀 기반)
대표적인 포맷은 JPEG, PNG입니다. 이들은 픽셀로 구성되어 있습니다. 예를 들어 2x2 픽셀인 비트맵 이미지는 총 4px로 구성되어 있습니다. 개개인에 대한 픽셀들은 자유자재로 바꿀 수가 없고 움직일 수도 없습니다. 그렇기 때문에 100% 이상으로 이미지를 확대하면 Pixelate가 됩니다.
SVG 그래픽: 벡터 기반
픽셀로 구성되어 있지 않고 작업하고 있는 그래픽에 대한 정보로 구성되어 있습니다. 그렇기 때문에 어떤 사이즈로든 자유자재로 늘어나는 것이 가능합니다. 이러한 이유들로 인해 코드로 쉽게 적용된 스타일을 수정할 수 있습니다. 예를 들어 동그라미의 보더 값을 6에서 8로 바꾼다 / 색상을 그레이에서 블랙으로 바꾼다 / 사이즈를 40x40에서 80x80을 바꾼다 등
스케치로 작업할 때도 쉽게 두 개의 차이점을 확인해볼 수 있습니다. 스케치에서 Export를 할 경우 비트맵 이미지는 하나의 압축된 레이어로 Export 됩니다. 반면 SVG는 레이어 그대로 눈에 보이지 않는 그래픽을 구성하는 정보들이 같이 저장된 채 Export가 됩니다.
다른 그래픽 포맷보다 SVG가 좋은 이유는 참으로도 다양합니다. 제가 생각했을 때의 핵심 장점들은 이러합니다.
스케치 하단 오른쪽 패널을 보면 Export 버튼이 있습니다. 여기서 Format을 SVG로 바꾸고 Export하면 금방 쉽게 끝나겠지 라고 생각할 수 있는데 여기서 조심해야 할 점은 본인이 어떻게 이미지를 작업했냐에 따라 옳지 않게 SVG가 내보내질 수 있습니다. 옳지 않게 SVG가 내보내 지게 되면 나중에 두 번 일을 작업하는 일이 발생할 수도 있습니다.
쉽게 이해하실 수 있도록 이미지를 제작해 보았습니다. 아래 이미지는 같은 디자인인데 만들어진 방식이 각각 다릅니다.
1. Two Shape
2. One Shape
3. Border and Shape Mix
위 3가지 방법들은 옳고 그름이 없습니다. 다만 어떻게 이 아이콘을 나중에 활용할 것인가에 따라 만드는 방법이 달라지겠죠. 만약에 자동차 아이콘 안에 헤드라이트 색상을 바꾸고 싶다고 하면 위 방법 중 1번을 선택하면 될 것이고 선의 두께를 따로 조정하고 싶다 하면 3번 방식을 택하면 됩니다.
SVG에 대해 잘 알지 못할 때는 프로그램 탓을 했었습니다. ‘왜 프로그램이 알아서 잘 못해주지?’라는 질문을 던졌지만… 슬프게도 이건 프로그램 잘못이 아닌 작업자 잘못입니다 �
스케치 프로그램이든 아도비 일러스트레이터든 이 프로그램들은 디자이너가 만든 그래픽을 있는 그대로 svg 레이어로 번역하도록 프로그램이 되어 있습니다. 디자이너가 어떻게 작업했냐에 따라 그 정보 그대로 인식해서 svg로 만들어줍니다.
다른 그래픽 포맷보다 SVG가 좋은 이유는 참으로도 다양합니다. 필자가 생각했을 때의 핵심 장점들은 이러합니다.
어느 날 SVG를 적용하기로 마음먹고 데일리호텔 앱 내 편의시설 아이콘 중 수영장 SVG 파일을 개발자에게 넘겼습니다. 근데 구멍이 뚫려야 할 곳이 채워져서 나오는데 원인을 모르고 헤매던 시절이 있었습니다. 미디엄에서 이 문제를 해결해줄 좋은 글을 발견하게 되었는데 난생처음 보는 단어가 2개 있었습니다.
Even-Odd, Non-Zero…
여기서 Even-Odd, Non-Zero의 차이점을 자세히 언급하기에는 너무 길어서 제가 참고한 미디엄 블로그 링크를 공유해드릴 테니 가서 보시면 이해하실 수 있을 것 같습니다. 작업하기에 앞서 꼭 읽어보시기를 권장합니다.
https://medium.com/sketch-app-sources/preparing-and-exporting-svg-icons-in-sketch-1a3d65b239bb
그래도 가볍게 필요한 내용만 공유드리자면 안드로이드에서는 fill-rule:evenodd를 제대로 지원하지 않고 fill-rule:nonzero만 지원한다고 보시면 됩니다. Even Odd는 특정 앱에서 호환이 안된다는 뜻입니다. (안드로이드 API 24 이상에서만 evenodd가 지원됨)
근데 우리가 사용하고 있는 스케치 프로그램에서는 default값이 fill-rule:evenodd로 설정이 되어있고 여러 Path가 겹치는 아이콘 같은 경우 그대로 svg export를 하게 되면 위에서 제가 경험하였던 아이콘이 다 채워진 현상을 겪을 수 있게 되는 것입니다.
1. Fills 섹션에서 Even-Odd를 Non-Zero로
Fills 섹션에 가면 설정 아이콘이 있습니다. 클릭 시 Even-Odd가 디폴트 값인 것을 확인할 수 있습니다.
Non-Zero로 설정값을 바꾸면 수영장 사다리 부분이 가득 채워진 채로 나오게 되는 것을 확인할 수 있습니다. 실제로 이 파일을 개발자에게 넘기게 되면 이렇게 채워진 채로 아이콘이 노출이 됩니다.
이렇게 나가면 안 될 테니 수정하는 법을 알려드리겠습니다.
2. Paths > Reverse Order 적용
원래 뚫려 있어야 하는 Path를 Layer 패널에서 찾으면 됩니다. 빨간색으로 칠한 부분이 뚫려있어야 하는 부분들입니다.
Path가 선택된 채로 Layers > Paths > Reverse Order을 클릭합니다.
Reverse Order을 클릭한 후 원래 뚫려있어야 하는 부분이 뚫리게 됩니다. 이 상태로 svg로 export하시고 개발자에게 전달을 하면 됩니다.
개인적으로 SVG에 대한 장점이 너무나도 크다고 생각하여 굳이 갈아타지 않을 이유가 없다고 생각합니다. 특히 Web 디자인을 할 때도 SVG를 저는 적극적으로 사용하시라고 권장하고 싶습니다. � 안드로이드 개발자에게 넘기기 전에 SVG 파일이 문제가 있는지 가볍게 확인하고 싶은 경우 아래와 같은 사이트를 추천해드립니다.
http://inloop.github.io/svg2android/
위에 문제가 되었던 수영장 아이콘을 이 사이트에 올려서 보게 되면 이런 화면이 뜹니다. Warning하고 노란색 경고 박스가 뜨게 되는데 fills-rule:evenodd에 대해서 언급을 하더라구요. 정말 유용한 사이트인 것 같습니다.
데일리 Product/Tech Blog : https://dailyhotel.io/
작성자 : Product팀 Rachel Kim