[네이버 지도] 행정구역 표시(shp -> geojson)
기타2021. 1. 7. 11:01
준비물: 시도 shp, 시군구 shp, 읍면동 shp
프로그램: mapshaper, QGIS, python 3.9.1
국내 행정구역 shp 파일은 용량도 크고 너무 세밀하게 표현된 부분이 많아서
웹에 단순한 행정구역을 표시할 때 용량과 속도 등에서 제약사항이 발생한다.
국내 행정구역 shp 파일에서 사용된 좌표계는 GRS80 (EPSG: 5179) 이므로
네이버 지도에서 사용하는 위도와 경도 좌표계 WGS84 (EPSG: 4326)로 변환해야 한다.
변환 과정 요약
1. mapshaper 등의 프로그램으로 simplify 과정을 거쳐 단순화(shp ▶ shp)
2. QGIS 등의 프로그램을 이용하여 WGS 84 좌표로 변환(shp ▶ json(geojson))
3. python 등을 이용해 전체 geojson 파일에서 필요한 행정구역 파일로 분할 저장(json ▶ json(geojson))
[시군구 geojson 분할 저장] python 3.9.1
//-------------------------------------- // 시군구 geojson 분할 저장 //-------------------------------------- #python 3.9.1 import json #json 파일 읽기 with open('d:\\sig_202005_wgs84.geojson', 'r', encoding='UTF8') as rf: geojson = json.load(rf) #시군구 반복 for item in geojson['features']: code = item['properties']['SIG_CD'] #행정구역코드 name = item['properties']['SIG_KOR_NM'] #행정구역명 item['id'] = code; #네이버 지도용 id 설정 #json 파일 저장 경로 path = 'd:\\sig\\'+ code +'.json' print(path +' '+ name) #json 객체 생성 geo = dict() geo['type'] = 'FeatureCollection' geo['features'] = [] #features는 배열 geo['features'].append(item) #json 파일 저장 with open(path, 'w', encoding='UTF8') as wf: json.dump(geo, wf, ensure_ascii=False) #한글 유니코드 저장 방지
[행정구역 json 파일 로드]
//-------------------------------------- // 행정구역 json 파일 로드 //-------------------------------------- var HOME_PATH = window.HOME_PATH || '.', urlPrefix = HOME_PATH +'/data/region', urlSuffix = '.json', regionGeoJson = [], loadCount = 0; // 행정구역 json 파일 로드 naver.maps.Event.once(map, 'init_stylemap', function () { for (var i = 1; i < 18; i++) { var keyword = i +''; if (keyword.length === 1) { keyword = '0'+ keyword; } $.ajax({ url: urlPrefix + keyword + urlSuffix, success: function(idx) { return function(geojson) { regionGeoJson[idx] = geojson; loadCount++; if (loadCount === 17) { startDataLayer(); } } }(i - 1) }); } });
[Geojson 파일 형태]
//-------------------------------------- // Geojson 파일 형태 //-------------------------------------- // 툴팁 설정 var tooltip = $('<div style="position: absolute; z-index: 1000; padding: 5px 10px; background-color: #fff; border: solid 2px #000; font-size: 14px; pointer-events: none; display: none;"> </div>'); tooltip.appendTo(map.getPanes().floatPane); // 로드된 행정구역은 아래와 같은 형태 regionGeoJson.push({ "type": "FeatureCollection", "features": [{ "id": "11140", "type": "Feature", "properties": {"SIG_CD": "11140", "SIG_ENG_NM": "Jung-gu", "SIG_KOR_NM": "중구"}, "geometry": { "type": "MultiPolygon", "coordinates": [[[ [127.0233653, 37.5719143], [127.0233917, 37.5719073], [127.0235305, 37.5671585], [127.0235359, 37.5669135], [127.0235319, 37.5668462], [127.0235326, 37.5668336], [127.0217938, 37.5575103], [127.0217328, 37.5575278], [127.0195773, 37.5574955], [127.0196807, 37.5572629], [127.0180939, 37.5568746], [127.0178901, 37.5567028], [127.0162301, 37.5528015], [127.0159829, 37.552589], [127.015938, 37.5525498], [127.015858, 37.552471], [127.0089881, 37.5441349], [127.0050173, 37.5461716], [127.0061278, 37.5481932], [127.0046885, 37.5486851], [127.0045604, 37.5498499], [127.0043733, 37.5501537], [127.0043557, 37.5501974], [127.0043362, 37.5502112], [127.0042094, 37.5501507], [127.0034213, 37.5500195], [127.0028642, 37.5496416], [127.0016841, 37.5500597], [126.9983251, 37.5496954], [126.9944593, 37.547488], [126.9787954, 37.5540872], [126.9724082, 37.5548773], [126.96571, 37.5541518], [126.963376, 37.552259], [126.962778, 37.551848], [126.9626113, 37.5517331], [126.9623428, 37.5515489], [126.9623691, 37.5516032], [126.962376, 37.5516286], [126.9624048, 37.5516477], [126.9623107, 37.55277], [126.9620066, 37.5540349], [126.9619314, 37.554448], [126.9617737, 37.5547951], [126.9617773, 37.554982], [126.9619781, 37.5551268], [126.9621418, 37.5555309], [126.9624769, 37.5559106], [126.9627196, 37.5559726], [126.9631727, 37.5565488], [126.9633575, 37.5566854], [126.9634369, 37.5568535], [126.9634273, 37.5569479], [126.9634093, 37.5569943], [126.963052, 37.5574148], [126.9630411, 37.5580298], [126.9620761, 37.5584566], [126.9615951, 37.5584184], [126.9617358, 37.5588129], [126.961711, 37.5589526], [126.9616892, 37.5589824], [126.9616726, 37.5590258], [126.962956, 37.5591763], [126.9632096, 37.5591958], [126.9633065, 37.5592155], [126.9668376, 37.561274], [126.9674439, 37.5615089], [126.9681526, 37.5616215], [126.969265, 37.5619273], [126.9694319, 37.5619679], [126.9694641, 37.5619758], [126.9693301, 37.5622305], [126.9689586, 37.5629149], [126.967562, 37.5648787], [126.9666982, 37.56582], [126.9668651, 37.5659861], [126.9668874, 37.5660078], [126.9966167, 37.5686865], [126.9968368, 37.5687099], [126.997025, 37.5687315], [127.0007881, 37.5693806], [127.0013078, 37.5694769], [127.014613, 37.5697183], [127.0147018, 37.5697206], [127.0176066, 37.5702101], [127.0177723, 37.5702912], [127.0233653, 37.5719143] ]]] } }] });
[행정구역 표시]
//-------------------------------------- // 행정구역 표시 //-------------------------------------- function startDataLayer() { map.data.setStyle(function(feature) { var styleOptions = { fillColor: '#ff0000', fillOpacity: 0.0001, strokeColor: '#ff0000', strokeWeight: 4, strokeOpacity: 0.4 }; if (feature.getProperty('focus')) { styleOptions.fillOpacity = 0.6; styleOptions.fillColor = '#0f0'; styleOptions.strokeColor = '#0f0'; styleOptions.strokeWeight = 4; styleOptions.strokeOpacity = 1; } return styleOptions; }); regionGeoJson.forEach(function(geojson) { map.data.addGeoJson(geojson); }); map.data.addListener('click', function(e) { var feature = e.feature; if (feature.getProperty('focus') !== true) { feature.setProperty('focus', true); } else { feature.setProperty('focus', false); } }); map.data.addListener('mouseover', function(e) { var feature = e.feature; var regionName = feature.getProperty('SIG_KOR_NM'); tooltip.css({ display: '', left: e.offset.x, top: e.offset.y }).text(regionName); map.data.overrideStyle(feature, { fillOpacity: 0.6, strokeWeight: 4, strokeOpacity: 1 }); }); map.data.addListener('mouseout', function(e) { tooltip.hide().empty(); map.data.revertStyle(); }); } startDataLayer();
참고
'기타' 카테고리의 다른 글
[네이버 지도] 마커 클러스터링 (0) | 2021.01.14 |
---|---|
[네이버 지도] 사용자 정의 오버레이 (0) | 2021.01.13 |
티스토리 SyntaxHighlighter 3.0.8.3 사용법 (0) | 2018.10.25 |
택배 조회 URL (0) | 2018.09.18 |
CSS 이미지 위에 텍스트 표시 (0) | 2018.08.20 |