안녕하세요 유저인사이트 박준호 선임입니다.
저는 이번에 GPS 데이터와 관련된 개발을 진행했는데, 개발하며 겪었던 문제들과 해결 과정들을 공유하고자 주제를 선정하였습니다.
GPS 표현 방식
먼저 GPS 데이터를 표현하는 방법에는 3가지가 있습니다.
1. GPS Data (3547.1282, 12707.2816)
2. 10진수 (35.35821, 127.58165)
3. 도분초 (35º21'14.34'' 127º26'17.97'')
3번 도분초는 개발 과정에서 사용하지 않으므로 따로 언급하지 않고 넘어가도록 하겠습니다.
GPS 기기로 데이터를 측정을 하게되면 첫 번째 형태의 데이터를 얻게 됩니다. 실제로는 NMEA 형식 데이터로 측정되는데 NMEA 형식은 밑에서 자세히 다루도록 하겠습니다.
두번째 10진수 형식은 지도에서 사용하는 데이터로, 일반적으로 사용하는 위도 경도 값입니다.
해당 값을 지도에 검색하면 해당 좌표의 위치가 나옵니다.
NMEA
NMEA는 시간, 위치, 방위 등을 전송하기 위한 규격으로 GPS 기기로 데이터를 측정하면 나오는 일련의 데이터들입니다.
GPS 데이터를 측정하면 많은 데이터를 얻을 수 있지만, 이 중 GNGGA만 필요하고, GNGGA 내에서도 일부만 사용합니다.
첫 번째, 유형은 간단하게 접두가 GP 와 GN 이 있는데 GP는 일반적인 GPS 값이라고 보면 되고, GN 이면 GNSS 보정을 받을 수 있는 데이터라고 생각하면 됩니다.
GNSS 는 GPS 데이터를 보정해주는 위성항법시스템으로 GPS 위성에서 발신한 전파를 이용하여 GPS 데이터를 보정해줍니다.
두번째, 위도 경도는 사용하려면 10진수 데이터로 만들어 줘야 하는데 만드는 과정은 이러합니다.
먼저 위도는 정수 부분의 가장 앞의 두 자리를 떼고, 남은 값을 60으로 나눠줍니다. 그 후 떼어낸 부분을 다시 붙이면 됩니다.
예) 3547.61679 -> 35 // 47.61679 / 60 -> 35 + 0.7936131 -> 35.79361
경도는 앞의 세자리를 떼고 위도와 같은 방법으로 계산하면 됩니다.
예) 12707.02264 -> 127 // 7.02264 / 60 -> 127 + 0.117044 -> 127.117044
세번째, FIX 는 Position Fix로 현재 GPS 데이터의 신뢰도를 나타냅니다.
1차 개발 - 오차 발생
위의 정보들을 토대로 1차 개발을 진행했습니다.
개발내용은 간단하게, 기존에 설정한 제원들과 GPS 기기로 측정한 좌표에 원을 그리는 작업입니다.
안드로이드에서 개발을 진행했기 때문에 canvas에 그렸습니다.
GPS 좌표는 canvas에 그리기 위해서 좌표를 임의로 정제하였고, 개발을 완료했습니다.
안드로이드 개발이 완료되고 웹에서 OpenLayers로 안드로이드의 화면과 동일한 화면을 추가 개발하던 도중 문제가 발견되었습니다.
겉보기에는 문제없이 원하는 위경도에 원하는 크기로 그려진 것 같았지만, 카카오맵에 실제 좌표와 반경으로 그린 모습과는 달랐고 문제를 찾기 시작했습니다.
가장 의심이 되는 부분은 안드로이드에서 canvas에 그릴 때 GPS 좌표를 내부적으로 정제한 일인데,
OpenLayers로 개발을 할 때도 어플에 개발한 모습과 거의 같아서 원인을 파악하지 못했고 다시 GPS 관련 정보를 찾다결국 원인을 찾게 되었습니다.
EPSG 코드
GPS 기기로 측정한 데이터는 WGS84 좌표계로 EPSG:4326 코드를 사용하고, 지구의 중심을 기준으로 만들어진 타원체 모델을 사용하여 좌표를 표현하는 특징이 있습니다.
따라서 WGS84 좌표계의 데이터를 직접 사용하면 오차가 생길 수 밖에 없었고,
결국 GIS 소프트웨어 개발을 할 때에는 해당 좌표계를 지도에 실제 사용하고 있는 좌표계로 변환을 해줘야만 했습니다.
OpenLayers는 기본적으로 EPSG:4326을 사용하고 있었고, 안드로이드에 직접 개발한 좌표계도 결국 EPSG:4326 였기 때문에 둘의 차이가 없었던 것이었습니다.
2차 개발 - EPSG 코드 변환
원인을 파악한 후 먼저 OpenLayers에서 사용하는 좌표들을 구글지도에서 사용중인 EPSG:3857 로 변환을 했습니다.
OpenLayers는 좌표계를 변환하는 메소드를 제공하고 있어 해당 코드를 사용했고,
해당 좌표계에 맞게 다시 코드를 작성하니 카카오맵에 그린 모습과 동일한 형태를 띠게 되었습니다.
이어서 안드로이드는 좌표계를 변환하는 메소드는 주로 GIS 관련 라이브러리가 제공하고, 좌표계를 직접 변환하기에는 어려움이 있었습니다.
안드로이드 뒷 배경은 구글지도를 사용하고 있고, 지도 위에 WSG84 데이터를 넣으면 라이브러리가 알아서 변환해주기 때문에 구글지도 위에 바로 그리는 방법으로 처음부터 다시 개발을 진행하기로 노선을 변경하였으며, 개발을 완료하게 되었습니다.
후기
처음 개발했던 당시에는 배경에 지도가 없어서인지 몰라도 실제 모습과 다르다는 문제가 있다고 파악조차도 못했었습니다.
GPS가 이동함에 따라 회전이 되고, 잘 그려진다는 데에만 만족했던 게 패인이었다고 생각합니다.
만약 당시에 문제를 미리 파악했다면, 좌표계에 대한 정보를 충분히 파악하고 있었더라면, 개발이 완료된 프로그램을 처음부터 다시 개발하는 일이 없었으리라 생각됩니다.
깊고 넓은 정보 검색의 중요성을 뼈저리게 느낀 계기가 되었습니다.
참고) EPSG:3857
+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs
박준호 / 선임연구원
Junho Park / 서비스R&D팀
'세미나' 카테고리의 다른 글
Svelte로 웹 개발을 간소화하기 (0) | 2023.04.13 |
---|---|
실무에서 사용하는 Spring Security Configuration (0) | 2023.04.04 |
Spring Boot 프로젝트에 Swagger 적용하기 (+인증) (1) | 2023.03.07 |
ChatGPT 체험 후기 (0) | 2023.02.24 |
Maven 프로젝트 Gradle로 변환하기 (0) | 2023.02.14 |