본문 바로가기
Web/Frontend

[Next.js] Naver Map API 이용해서 현재 위치 지도 띄우기

by r4bb1t 2023. 11. 15.
반응형

[NextJS 지도 개발 #1] next/script를 이용하여 네이버 지도 API를 이용하자 글을 많이 참고하였습니다. 감사합니다.

우선 네이버 지도 API 사용 신청을 합니다. (https://www.ncloud.com/product/applicationService/maps)

Application 등록을 클릭하여,

사용할 API를 추가해줍니다.

로컬호스트도 등록 가능합니다. (이후에 배포 시에는 삭제합니다.)

인증 정보를 클릭하면,

클라이언트 아이디와 시크릿이 나오는데, 이를 복사하여 .env에 넣어줍니다.

NEXT_PUBLIC_MAP_CLIENT_ID=
NEXT_PUBLIC_MAP_CLIENT_SECRET=

맵의 타입을 선언해줍니다. (map.d.ts)

pnpm i -D @types/navermaps

사용하는 패키지 관리자로 @types/navermaps를 추가해줍니다.

export type NaverMap = naver.maps.Map;
type Lng = number;
type Lat = number;
export type Coordinates = [Lng, Lat];

이후 맵을 사용할 컴포넌트를 클라이언트 컴포넌트로 선언하고 코드를 작성합니다.

"use client";

import Script from "next/script";
import { Coordinates, NaverMap } from "@/app/types/map";
import { useCallback, useRef } from "react";

const mapId = "naver-map";

export default function Map({ loc }: { loc: Coordinates }) {
  const mapRef = useRef<NaverMap>();

  const initializeMap = useCallback(() => {
    const mapOptions = {
      center: new window.naver.maps.LatLng(loc),
      zoom: 15,
      scaleControl: true,
      mapDataControl: true,
      logoControlOptions: {
        position: naver.maps.Position.BOTTOM_LEFT,
      },
    };
    const map = new window.naver.maps.Map(mapId, mapOptions);
    mapRef.current = map;
  }, [loc]);

  return (
    <>
      <Script
        strategy="afterInteractive"
        type="text/javascript"
        src={`https://openapi.map.naver.com/openapi/v3/maps.js?ncpClientId=${process.env.NEXT_PUBLIC_MAP_CLIENT_ID}`}
        onReady={initializeMap}
      ></Script>
      <div id={mapId} style={{ width: "100%", height: "100%" }} />
    </>
  );
}

최초 맵 시작 위치인 loc을 prop으로 뺀 이유는, 맵을 감싸고 있는 컨테이너에서 navigator.geolocation API로 현재 위치를 받아오기 위함입니다. 필요 없는 경우 그냥 위도와 경도를 넣어주면 됩니다.

"use client";

import { useEffect, useState } from "react";
import { Coordinates } from "@/app/types/map";
import Map from ".";

export default function MapContainer() {
  const [loc, setLoc] = useState<Coordinates>();

  const initLocation = () => {
    navigator.geolocation.getCurrentPosition((position) => {
      setLoc([position.coords.longitude, position.coords.latitude]);
    });
  };

  useEffect(() => {
    initLocation();
  }, []);

  return loc && <Map loc={loc} />;
}

navigator.geolocation에서 현재 위치를 받아온 후 Map을 렌더링할 MapContainer 컴포넌트입니다. 현재 유저의 위치가 세팅되면 맵을 렌더링합니다.

실제 제 현재 위치는 아닙니다.

맵이 필요한 곳에서 <MapContainer />를 가져와주면, 이렇게 현재 위치를 중심으로 한 맵이 렌더링되는 것을 볼 수 있습니다.

반응형

댓글