우리나라의 위도와 경도값을 토대로 캔버스에 그려준 뒤에 이벤트를 부여하는 기능입니다.
우리나라 지도의 차트기능 만들 때 사용하였습니다.
우리나라의 위도경도 값은 구글링하면 쉽게 받을 수 있습니다.
"대한민국 최신 행정구역(shp)" 이라는 주제로 검색하면 다양한 정보를 받을 수 있습니다.
해당 shp파일은 웹에서 표현하기 어려운 값으로 되어 있습니다.
shp to geojson이라는 내용으로 검색하여 json형식의 위도, 경도값으로 나오도록 파싱하여 줍니다.
* 예 : mygeodata.cloud/converter/shp-to-geojson
파싱을 하고난 뒤에 json 내용을 열어보았습니다.
이제 위도 경도 값을 가져왔으니 캔버스에 그려주어야 합니다.
위도와 경도값을 평면에 나타 내려면 각 값에서 일정한 계산법이 들어가야 합니다.
function makeLine(data){ //data는 위도경도 지점 입니다.
var x = data[0] / 360 * 500; //경도는 180 ~ -180까지이며 구면체에 대한 500을 곱해줍니다.
var y = data[1] / 180 * 500; //위도는 90~ -90까지이며 구면체에 대한 500을 곱해줍니다.
var finalX = canvas.width - canvas.width*0.2 - - Math.abs((x - 180) * 100 * 0.55); //그리는 화면에 대한 비율계산
var finalY = canvas.height -Math.abs((y - 90) * 100 * 0.55);//그리는 화면에 대한 비율계산
return {x:finalX, y : finalY};
}
위 makeLine함수를 토대로 위경도 값을 캔버스에서 적용하는 값으로 변환하여 줍니다.
캔버스에서 그릴 때는 moveTo와 lineTo로 구현하였습니다.
그리고 선 그리기가 끝난 이후에는 색상을 fill 함수를 통해서 채워 주었습니다.
이렇게 그려주면..아래 사진처럼 캔버스에 우리나라 지도를 나타낼 수 있습니다.
이제 그러면 각 지역별 이름을 달아주어야됩니다.
이름을 넣어주는 방법은 각 x점과 y점의 최대값과 최소값을 구한뒤에 절반으로 나누어 구할 수 있습니다.
서울을 예로들면,
서울을 그릴 때 모든 x와 모든 y를 가져와서 해당 값에서 가장 작은 x와 y를 넣어줍니다.
그리고 가장 큰 x와 가장 큰y를 넣어준 뒤에 두 합을 구해서 절반되는 값을 가져오면 됩니다.
function innerDataArrayMaker(inner_dataArray, textJson, finalX, finalY){
var center = _getCenterPos(textJson.minX, textJson.minY, finalX, finalY);
textJson.minX = center.x;
textJson.minY = center.y;
center = _getCenterPos2(textJson.maxX, textJson.maxY, finalX, finalY);
textJson.maxX = center.x;
textJson.maxY = center.y;
inner_dataArray.push({ x: finalX, y: finalY });
return textJson;
}
//innerDataArrayMaker 종속 함수1
function _getCenterPos(inn_x, inn_y, data_x, data_y){
if(data_x < inn_x){
inn_x = data_x;
}
if(data_y < inn_y){
inn_y = data_y;
}
return {x : inn_x, y : inn_y};
}
//innerDataArrayMaker 종속 함수2
function _getCenterPos2(inn_x, inn_y, data_x, data_y){
if(data_x > inn_x){
inn_x = data_x;
}
if(data_y > inn_y){
inn_y = data_y;
}
return {x : inn_x, y : inn_y};
}
이름이 겹치는 부분이 존재한다면 해당 값을 조금씩 조정해주면 아래사진처럼 이름이 들어가 모양을 볼 수 있습니다.
여기까지 하고나면 뭔가 허전한게...
마우스를 올리면 이벤트가 좀 나타났으면 좋겠습니다(?)
마우스 이벤트를 적용하려면 다각형에 대한 이벤트를 적용하는 계산방법이 들어가야 합니다.
예전에 포스팅한 글을 참조하여주세요~
* 참조 : lts0606.tistory.com/286
어떤분인지 몰라도 저러한 계산방법을 구했다는 것에 대해서 정말 대단함을 느꼈습니다.
계산하는 함수의 내용은 아래와 같습니다.
//다각형에서의 접선 구하는 함수
function isInside(event) {
//crosses는 점과 오른쪽 반직선과 다각형과의 교점의 개수
var result = false;
for(var mm = 0 ; mm < dataArray.length; mm++){
var cross = 0;
var position = dataArray[mm];
for (var i = 0; i < position.value.length; i++) {
var pos = position.value[i];
var j = (i + 1) % position.value.length; //교점구할 j값, 1,2,3..순으로 인덱스가 증가하다 마지막은 초기값 0이 나와 비교를 함.
var otherPos = position.value[j];
if ((pos.y > event.y) != (otherPos.y > event.y)) { //점 event가 선분에 있는지 여부
var visit = (otherPos.x - pos.x) * (event.y - pos.y) / (otherPos.y - pos.y) + pos.x;
if (event.x < visit){
cross++;
}
}
}
if(cross % 2 > 0){
result = position.key;
}
}
return result; //홀짝 후 리턴
}
위 함수를 캔버스에 적용한 뒤에, 마우스의 위치가 이벤트 지점에 도달하면 캔버스를 지우고 해당 이벤트 지역에 대해서 배경색이 바뀌면서 글씨가 굵어지도록 하게 하였습니다.
나름 괜찮은 작업이였던 것 같습니다.
물론, 마우스를 통해서 zoom 이벤트와 zoom이 된 이후에 drag이벤트 기능은 추가적인 공수(?)가 많이 들어서 포기하였던 것 같습니다...ㅠㅠ
역시 이래서 상용화된 차트를 많이 쓰는가 봅니다.
해당 포스팅은 코드를 전부 공개하지 않고 개념만 정리한 내용입니다.
이상으로 Html 캔버스를 활용하여 우리나라 지도를 그리는 내용에 대해서 살펴 보았습니다.
문의사항이나 궁금한 점은 댓글 또는 메일로 연락주세요 :)
'Html 캔버스 > Html 캔버스 에니메이션' 카테고리의 다른 글
Html Canvas에 대한민국 지도 쉽계 계산하여 표현 하기 (0) | 2021.04.08 |
---|---|
Html Korea map, Html 캔버스 대한민국 지도(차트 스타일) (1) | 2021.03.19 |
Html canvas 그리는 좌표 저장 기능(x, y position) (3) | 2021.03.04 |
Html Canvas circle agenda, Html 캔버스 원형 시간표(circle schedule, 방학 시간표) 제작기 (0) | 2021.02.15 |
Html Canvas mosaic, Html 캔버스 모자이크 기능 제작 (12) | 2020.08.27 |
댓글