Nhóm điểm đánh dấu

Chọn nền tảng: Android iOS JavaScript

Tổng quan

Hướng dẫn này cho bạn biết cách sử dụng các cụm điểm đánh dấu để hiển thị một số lượng lớn điểm đánh dấu trên bản đồ. Bạn có thể dùng thư viện @googlemaps/markerclusterer kết hợp với API JavaScript của Maps để kết hợp các điểm đánh dấu vùng lân cận thành các cụm và đơn giản hoá việc hiển thị các điểm đánh dấu trên bản đồ.

Để xem cách hoạt động của tính năng phân cụm điểm đánh dấu, hãy xem bản đồ bên dưới.

Số trên một cụm cho biết có bao nhiêu điểm đánh dấu. Lưu ý rằng khi bạn phóng to bất kỳ vị trí cụm nào, số trên cụm sẽ giảm và bạn bắt đầu nhìn thấy các điểm đánh dấu riêng lẻ trên bản đồ. Khi thu nhỏ bản đồ, các điểm đánh dấu sẽ được hợp nhất lại thành các cụm.

Mẫu dưới đây cho thấy toàn bộ mã bạn cần để tạo bản đồ này.

TypeScript

async function initMap() {
  // Request needed libraries.
  const { Map, InfoWindow } = await google.maps.importLibrary("maps") as google.maps.MapsLibrary;
  const { AdvancedMarkerElement, PinElement } = await google.maps.importLibrary("marker") as google.maps.MarkerLibrary;

  const map = new google.maps.Map(
    document.getElementById("map") as HTMLElement,
    {
      zoom: 3,
      center: { lat: -28.024, lng: 140.887 },
      mapId: 'DEMO_MAP_ID',
    }
  );

  const infoWindow = new google.maps.InfoWindow({
    content: "",
    disableAutoPan: true,
  });

  // Create an array of alphabetical characters used to label the markers.
  const labels = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";

  // Add some markers to the map.
  const markers = locations.map((position, i) => {
    const label = labels[i % labels.length];
    const pinGlyph = new google.maps.marker.PinElement({
      glyph: label,
      glyphColor: "white",
    })
    const marker = new google.maps.marker.AdvancedMarkerElement({
      position,
      content: pinGlyph.element,
    });

    // markers can only be keyboard focusable when they have click listeners
    // open info window when marker is clicked
    marker.addListener("click", () => {
      infoWindow.setContent(position.lat + ", " + position.lng);
      infoWindow.open(map, marker);
    });
    return marker;
  });

  // Add a marker clusterer to manage the markers.
  new MarkerClusterer({ markers, map });
}

const locations = [
  { lat: -31.56391, lng: 147.154312 },
  { lat: -33.718234, lng: 150.363181 },
  { lat: -33.727111, lng: 150.371124 },
  { lat: -33.848588, lng: 151.209834 },
  { lat: -33.851702, lng: 151.216968 },
  { lat: -34.671264, lng: 150.863657 },
  { lat: -35.304724, lng: 148.662905 },
  { lat: -36.817685, lng: 175.699196 },
  { lat: -36.828611, lng: 175.790222 },
  { lat: -37.75, lng: 145.116667 },
  { lat: -37.759859, lng: 145.128708 },
  { lat: -37.765015, lng: 145.133858 },
  { lat: -37.770104, lng: 145.143299 },
  { lat: -37.7737, lng: 145.145187 },
  { lat: -37.774785, lng: 145.137978 },
  { lat: -37.819616, lng: 144.968119 },
  { lat: -38.330766, lng: 144.695692 },
  { lat: -39.927193, lng: 175.053218 },
  { lat: -41.330162, lng: 174.865694 },
  { lat: -42.734358, lng: 147.439506 },
  { lat: -42.734358, lng: 147.501315 },
  { lat: -42.735258, lng: 147.438 },
  { lat: -43.999792, lng: 170.463352 },
];

initMap();

JavaScript

async function initMap() {
  // Request needed libraries.
  const { Map, InfoWindow } = await google.maps.importLibrary("maps");
  const { AdvancedMarkerElement, PinElement } = await google.maps.importLibrary(
    "marker",
  );
  const map = new google.maps.Map(document.getElementById("map"), {
    zoom: 3,
    center: { lat: -28.024, lng: 140.887 },
    mapId: "DEMO_MAP_ID",
  });
  const infoWindow = new google.maps.InfoWindow({
    content: "",
    disableAutoPan: true,
  });
  // Create an array of alphabetical characters used to label the markers.
  const labels = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
  // Add some markers to the map.
  const markers = locations.map((position, i) => {
    const label = labels[i % labels.length];
    const pinGlyph = new google.maps.marker.PinElement({
      glyph: label,
      glyphColor: "white",
    });
    const marker = new google.maps.marker.AdvancedMarkerElement({
      position,
      content: pinGlyph.element,
    });

    // markers can only be keyboard focusable when they have click listeners
    // open info window when marker is clicked
    marker.addListener("click", () => {
      infoWindow.setContent(position.lat + ", " + position.lng);
      infoWindow.open(map, marker);
    });
    return marker;
  });

  // Add a marker clusterer to manage the markers.
  new MarkerClusterer({ markers, map });
}

const locations = [
  { lat: -31.56391, lng: 147.154312 },
  { lat: -33.718234, lng: 150.363181 },
  { lat: -33.727111, lng: 150.371124 },
  { lat: -33.848588, lng: 151.209834 },
  { lat: -33.851702, lng: 151.216968 },
  { lat: -34.671264, lng: 150.863657 },
  { lat: -35.304724, lng: 148.662905 },
  { lat: -36.817685, lng: 175.699196 },
  { lat: -36.828611, lng: 175.790222 },
  { lat: -37.75, lng: 145.116667 },
  { lat: -37.759859, lng: 145.128708 },
  { lat: -37.765015, lng: 145.133858 },
  { lat: -37.770104, lng: 145.143299 },
  { lat: -37.7737, lng: 145.145187 },
  { lat: -37.774785, lng: 145.137978 },
  { lat: -37.819616, lng: 144.968119 },
  { lat: -38.330766, lng: 144.695692 },
  { lat: -39.927193, lng: 175.053218 },
  { lat: -41.330162, lng: 174.865694 },
  { lat: -42.734358, lng: 147.439506 },
  { lat: -42.734358, lng: 147.501315 },
  { lat: -42.735258, lng: 147.438 },
  { lat: -43.999792, lng: 170.463352 },
];

initMap();

CSS

/* 
 * Always set the map height explicitly to define the size of the div element
 * that contains the map. 
 */
#map {
  height: 100%;
}

/* 
 * Optional: Makes the sample page fill the window. 
 */
html,
body {
  height: 100%;
  margin: 0;
  padding: 0;
}

HTML

<html>
  <head>
    <title>Marker Clustering</title>

    <link rel="stylesheet" type="text/css" href="./style.css" />
    <script type="module" src="./index.js"></script>
  </head>
  <body>
    <div id="map"></div>

    <!-- prettier-ignore -->
    <script>(g=>{var h,a,k,p="The Google Maps JavaScript API",c="google",l="importLibrary",q="__ib__",m=document,b=window;b=b[c]||(b[c]={});var d=b.maps||(b.maps={}),r=new Set,e=new URLSearchParams,u=()=>h||(h=new Promise(async(f,n)=>{await (a=m.createElement("script"));e.set("libraries",[...r]+"");for(k in g)e.set(k.replace(/[A-Z]/g,t=>"_"+t[0].toLowerCase()),g[k]);e.set("callback",c+".maps."+q);a.src=`https://maps.${c}apis.com/maps/api/js?`+e;d[q]=f;a.onerror=()=>h=n(Error(p+" could not load."));a.nonce=m.querySelector("script[nonce]")?.nonce||"";m.head.append(a)}));d[l]?console.warn(p+" only loads once. Ignoring:",g):d[l]=(f,...n)=>r.add(f)&&u().then(()=>d[l](f,...n))})
        ({key: "AIzaSyB41DRUbKWJHPxaFjMAwdrzWzbVKartNGg", v: "weekly"});</script>
  </body>
</html>

Thử dùng mẫu

Một hình minh hoạ đơn giản, hướng dẫn này thêm một tập hợp các điểm đánh dấu vào bản đồ bằng cách sử dụng mảng locations. Bạn có thể sử dụng các nguồn khác để nhận điểm đánh dấu cho bản đồ của mình. Để biết thêm thông tin, hãy đọc hướng dẫn tạo điểm đánh dấu.

Thêm một cụm điểm đánh dấu

Làm theo các bước bên dưới để thêm một cụm điểm đánh dấu:

  1. Thêm thư viện phân cụm điểm đánh dấu vào trang hoặc ứng dụng của bạn. Bạn có thể xem thư viện này trên Trình quản lý nội dung của Google (N) tại @googlemaps/markerclusterer và trong kho lưu trữ trên GitHub.

    Điều khoản Dịch vụ (Nhà quảng cáo của Google)

    Cài đặt phiên bản mới nhất của thư viện @googlemaps/markerclusterer bằng cách sử dụng TLD.

    npm install @googlemaps/markerclusterer

    Mạng phân phối nội dung (CDN)

    Tập lệnh dưới đây tải phiên bản 1.x.x mới nhất của thư viện từ unpkg.com CDN.

    <script src="https://unpkg.com/@googlemaps/markerclusterer/dist/index.min.js"></script>
  2. Thêm một cụm điểm đánh dấu trong ứng dụng của bạn.

    Mã dưới đây thêm một cụm điểm đánh dấu vào bản đồ.

    Điều khoản Dịch vụ (Nhà quảng cáo của Google)

    import { MarkerClusterer } from "@googlemaps/markerclusterer";
    
    const markerCluster = new MarkerClusterer({ markers, map });

    Mạng phân phối nội dung (CDN)

    Khi được truy cập bằng CDN, thư viện này sẽ có trong toàn bộ markerClusterer.

    const markerCluster = new markerClusterer.MarkerClusterer({ markers, map });

    Mẫu này truyền mảng markers đến MarkerClusterer.

  3. Tuỳ chỉnh tính năng phân cụm điểm đánh dấu.

Tìm hiểu thêm

Bạn có thể xem các ví dụ phức tạp hơn về việc phân cụm điểm đánh dấu trong kho lưu trữ trên GitHub và đọc tài liệu tham khảo về thư viện này.