brunch

You can make anything
by writing

C.S.Lewis

by 갱그리 Jul 04. 2016

다음지도API로
다중 맵 동적 구현하기

7/4 개발일기

홈페이지를 개발하던 중, 가장 간단할 거라고 예상했던 회사 소개 페이지에서 막혔다. 문제는 다음지도 API 를 사용하여 약도를 구현하는데, 지도가 제대로 뜨지 않았다. 이 페이지는 Tab bar로 구현되어 있어 요소들의display 속성에 none, block 을 번갈아 주는데 찾아보니 이 때문에 일어난 일이었다. 요약하면 아래와 같다



-문제현상   :  Tab 타입으로 지도를 여러개 구현할 경우 지도가 제대로 로드되지 않음. 

-문제원인 : map을 생성할 때 currentStyle을 갖고 오는데, display 속성의 경우 해당 요소의 width/height 값을 삭제함. 이 때문에 map이 제대로 생성되지 않으면서 발생한 문제임.

-문제해결 : 요소의 width, height 를 보장하면서 가시성 여부만 바꿔주는 visibility 로 지도 div를 제어한다. 겸사겸사 동적으로, 최대한 소스는 깔끔하게 해보자.



이번에 알았는데 .append() 를 사용해 div를 생성할 경우, 해당 function 이 끝나지 않는한 javascript에서는 그 div를 제대로 생성된 것으로 여기지 않는다. 처음에는 .append() 로 map을 동적 생성해주려 했으나 잘 되지 않았던 이유였다. 


예컨대 아래처럼 append 를 하고 출력하면,

parentDiv.append("<div id='child' class='map' style='height:400px;'></div>");


각각 값이 다르게 나온다. jQuery 는 append 된 div의 스타일을 정확히 인식하는 반면

plain javascript 는 그렇지 않았다.


console.log($('#child').css("height"));  // 400px

console.log(document.getElementById('child').clientHeight); //0

console.log(document.getElementById('child').style.height); //undefined



나는 bootstrap에서 제공하는 tab 스타일을 썼다.

이 경우 다음지도 API 다중 맵을 동적 생성하는 소스는 아래와 같다. 


$("[role='tab']").click(function(){

        //다른 지도들은 hidden 처리한다

        $('.map').css("visibility","hidden"); 

        

        //target이 되는 탭 패널 div와 지도를 선택한다

        var target = $(this).attr("aria-controls");

        var targetMap = $(this).attr("aria-controls") + "-map";

        

        //target이 되는 지도만 visible 처리한다.

        $("#"+targetMap).css("visibility","visible");


        //지도에 param 속성으로 부여되어 있는 위도, 경도 값을 갖고 온다        

        var lat = $("#"+targetMap).attr("param").split(":")[0];

        var lng = $("#"+targetMap).attr("param").split(":")[1];


         mapContainer = document.getElementById(targetMap), 

            mapOption = { 

                center: new daum.maps.LatLng(lat, lng),

                level: 3 

            };

          var map = new daum.maps.Map(mapContainer, mapOption);

          map.relayout();  //지도 레이아웃을 재로딩한다

    });

})


내 경우 탭 패널 div의 ID와 지도가 들어갈 영역의 div ID를 비슷하게 맞추었다. 

tab 패널 div ID가 kangbuk 인 경우 map의 ID는 kangbuk-map 이다. 




HTML 소스는 아래와 같다(bootstrap tab 스타일)


bootstrap 기반 tab nav html 

<li role="presentation">

    <a href="#kangbuk" aria-controls="kangbuk" role="tab" data-toggle="tab">

        강북지점

    </a>

</li>


tab 패널 div

<div role="tabpanel" class="tab-pane active" id="kangbuk">


지도 div (tab-content 바깥에 둔다)

<div id="kangbuk-map" class="map" param="37.00000:126.00000"></div>

여기서 param은 내가 위도와 경도 값을 관리하기 위해 별도로 준 속성값이다. 이렇게 하면 위도와 경도를 다른 변수로 관리해야 할 필요도 없고 수정도 쉬워 코드가 한결 깔끔해진다.

브런치는 최신 브라우저에 최적화 되어있습니다. IE chrome safari