본문 바로가기
나의 정보/정보

[PHP] 사진의 EXIF에 포함된 GPS 좌표 변환(도분초를 도로 변환)

by 상오기™ 2009. 8. 21.
GPS가 내장된 카메라로 찍은 사진이나 GPS 로거를 이용하여 지오태깅을하면 사진의 EXIF에 GPS 정보가 입력이 됩니다.


PC에서 EXIF를 볼 수 있는 프로그램으로 확인을 하면 아래와 같이 입력된 GPS 정보를 볼 수 있습니다.

GPS information: - 
GPSVersionID - 2.2.0.0
GPSLatitudeRef - N
GPSLatitude - 36  26  0.69 => 위도: 36.433525° N
GPSLongitudeRef - E
GPSLongitude - 127  33  51.34 => 경도: 127.564262° E
GPSAltitudeRef - Sea level
GPSAltitude - 96.73 m


PHP의 exif_read_data() 함수를 이용하여 사진의 EXIF에 포함된 GPS 정보는 아래와 같이 표시 됩니다.

[GPSVersion] =>

[GPSLatitudeRef] => N
[GPSLatitude] => Array
    (
        [0] => 36/1 <- 문자열이라 숫자로 변환하여 계산을 함
        [1] => 26/1
        [2] => 5655/8192
    )

[GPSLongitudeRef] => E
[GPSLongitude] => Array
    (
        [0] => 127/1
        [1] => 33/1
        [2] => 71369/1390
    )

[GPSAltitudeRef] => 
[GPSAltitude] => 67612/699



GPS 좌표는 도분초로 입력이 되며 좌표값은 문자열이기 때문에 문자열을 숫자로 변환하여 실제 좌표값을 구해야 합니다.

도분초를 도로 변환하는건 함수로 만들면 깔끔하겠지만 변환하는게 몇개 안되므로 그냥 복사-붙여넣기 신공으로 처리 ㅡㅡ

$exif = @exif_read_data("temp.jpg", 0, true);

if ($exif) {
    $gps_lat = null;
    $gps_lon = null;
    $gps_ele = null;
    if ($exif["GPS"]) { //GPS 정보가 있다면
        if ($exif["GPS"]["GPSLatitude"] && $exif["GPS"]["GPSLongitude"]) { //위경도 좌표가 있다면
            list($temp_d1, $temp_d2) = sscanf($exif["GPS"]["GPSLatitude"][0], "%d/%d"); //문자->숫자로 계산
            $gps_lat_d = $temp_d1/$temp_d2;
            list($temp_d1, $temp_d2) = sscanf($exif["GPS"]["GPSLatitude"][1], "%d/%d");
            $gps_lat_m = $temp_d1/$temp_d2;
            list($temp_d1, $temp_d2) = sscanf($exif["GPS"]["GPSLatitude"][2], "%d/%d");
            $gps_lat_s = $temp_d1/$temp_d2;
            
            list($temp_d1, $temp_d2) = sscanf($exif["GPS"]["GPSLongitude"][0], "%d/%d"); //문자->숫자로 계산
            $gps_lon_d = $temp_d1/$temp_d2;
            list($temp_d1, $temp_d2) = sscanf($exif["GPS"]["GPSLongitude"][1], "%d/%d");
            $gps_lon_m = $temp_d1/$temp_d2;
            list($temp_d1, $temp_d2) = sscanf($exif["GPS"]["GPSLongitude"][2], "%d/%d");
            $gps_lon_s = $temp_d1/$temp_d2;
            
            $gps_lat = $gps_lat_d+$gps_lat_m/60+$gps_lat_s/3600; //도분초를 도로 변환
            $gps_lon = $gps_lon_d+$gps_lon_m/60+$gps_lon_s/3600;
            
            list($temp_d1, $temp_d2) = sscanf($exif["GPS"]["GPSAltitude"], "%d/%d"); //문자->숫자로 계산
            $gps_ele = $temp_d1/$temp_d2;
            
            echo "GPS lat d, m, s : $gps_lat_d, $gps_lat_m, $gps_lat_s<br />";
            echo "GPS lon d, m, s : $gps_lon_d, $gps_lon_m, $gps_lon_s<br />";
            //echo "GPS lat, lon, ele : $gps_lat, $gps_lon, $gps_ele<br />";
        }
    }
}


도분초를 도로 변환하는 이유는 구글맵에서 사용하기 위해선 도로 변환된 위, 경도 좌표가 필요하기 때문 입니다.

피카사 웹앨범에 등록된 지오태깅 사진

피카사 웹앨범에 등록된 지오태깅 사진


다음 지도는 콩나물 좌표계를 사용하므로 또 다른 좌표 변환이 필요 합니다.




좌표 변환은 공식을 이용하여 직접 계산할수도 있지만 다음 좌표변환 API를 이용하면 다양한 좌표로 손쉽게 변환이 가능 합니다.


야후에서도 다음 API와 같이 다양한 좌표 변환이 가능 합니다.

그런데 야후는 일정시간안에 일정횟수가 넘어가면 IP를 차단해 버립니다.
(예를들어 좌표 100개를 루프 돌려서 한번에 변환하면 IP 차단 당함)
하루정도 지나면 풀리긴 합니다만 오픈 API로 사용하라고 기능 만들어놓고 블록하는건 뭔 경우인지...^^;
1시간에 한두개만 변환하라는 뜻인가요? ㅡㅡ




이 글은 '상오기 : 자전거 여행과 GPS~!' 의 "상오기™ (sangogi@gmai.com)" 이 작성 하였습니다.
"상업적 이용 금지, 원본 출처(링크 포함) 및 저작자 표시, 내용 변경 금지"의 조건으로 자유롭게 사용하실 수 있으며 저작권에 대한 자세한 내용은 "저작권 안내를 참고 하시기 바랍니다.