Слои KML и GeoRSS

Выберите платформу: Android iOS JavaScript

Компонент KmlLayer преобразует элементы KML и GeoRSS в тайлы, отображаемые в формате Maps JavaScript API.

Обзор

API JavaScript для работы с картами поддерживает форматы данных KML и GeoRSS для отображения географической информации. Эти форматы данных отображаются на карте с помощью объекта KmlLayer , конструктор которого принимает URL-адрес общедоступного файла KML или GeoRSS.

Примечание: Класс KmlLayer , генерирующий KML-наложения в JavaScript API карт, использует сервис Google для получения и анализа KML-файлов для отображения. Следовательно, отображение KML-файлов возможно только в том случае, если они размещены по общедоступному URL-адресу, для доступа к которому не требуется аутентификация.

Если вам необходим доступ к закрытым файлам, точный контроль над кэшем или передача области просмотра браузера на сервер геопространственных данных в качестве параметра запроса, мы рекомендуем использовать слои данных вместо KmlLayer . Это позволит браузерам ваших пользователей напрямую запрашивать ресурсы с вашего веб-сервера.

API Maps JavaScript преобразует предоставленные географические XML-данные в KML-представление, которое отображается на карте с помощью тайлового наложения Maps JavaScript API. Этот KML-файл выглядит (и в некоторой степени ведет себя) как знакомые элементы наложения Maps JavaScript API. KML point элементы <Placemark> и GeoRSS отображаются как маркеры, например, элементы <LineString> отображаются как полилинии, а элементы <Polygon> — как полигоны. Аналогично, элементы <GroundOverlay> отображаются на карте как прямоугольные изображения. Важно отметить, однако, что эти объекты не являются Markers , Polylines , Polygons или GroundOverlays из Maps JavaScript API; вместо этого они отображаются на карте как единый объект.

Объекты KmlLayer появляются на карте после того, как для них установлено свойство map . Вы можете удалить их с карты, вызвав setMap() с передачей значения null . Объект KmlLayer управляет отрисовкой этих дочерних элементов, автоматически получая соответствующие объекты для заданных границ карты. По мере изменения границ объекты в текущей области просмотра автоматически отображаются.

Поскольку компоненты внутри KmlLayer отображаются по запросу, этот слой позволяет легко управлять отрисовкой тысяч маркеров, полилиний и многоугольников. Обратите внимание, что вы не можете получить прямой доступ к этим составляющим объектам, хотя каждый из них предоставляет события клика, которые возвращают данные для этих отдельных объектов.

Параметры слоя KML

Конструктор KmlLayer() может опционально передавать ряд параметров KmlLayerOptions :

  • map задаёт Map на которой будет отображаться KmlLayer . Вы можете скрыть KmlLayer , установив это значение в null в методе setMap() .
  • preserveViewport указывает, что карта не должна подстраиваться под границы содержимого KmlLayer при отображении слоя. По умолчанию при отображении KmlLayer карта масштабируется и позиционируется таким образом, чтобы показать все содержимое слоя.
  • suppressInfoWindows указывает, что кликабельные элементы внутри KmlLayer не должны вызывать отображение объектов InfoWindow .

Кроме того, после рендеринга KmlLayer он содержит неизменяемое свойство metadata включающее имя слоя, описание, фрагмент кода и автора в виде литерала объекта KmlLayerMetadata . Вы можете просмотреть эту информацию с помощью метода getMetadata() . Поскольку рендеринг объектов KmlLayer требует асинхронной связи с внешним сервером, вам следует отслеживать событие metadata_changed , которое будет указывать на то, что свойство было заполнено.

В следующем примере создается KmlLayer на основе заданного GeoRSS-канала:

Машинопись

function initMap(): void {
  const map = new google.maps.Map(
    document.getElementById("map") as HTMLElement,
    {
      zoom: 4,
      center: { lat: 49.496675, lng: -102.65625 },
    }
  );

  const georssLayer = new google.maps.KmlLayer({
    url:
      "http://api.flickr.com/services/feeds/geo/?g=322338@N20&lang=en-us&format=feed-georss",
  });
  georssLayer.setMap(map);
}

declare global {
  interface Window {
    initMap: () => void;
  }
}
window.initMap = initMap;

JavaScript

function initMap() {
  const map = new google.maps.Map(document.getElementById("map"), {
    zoom: 4,
    center: { lat: 49.496675, lng: -102.65625 },
  });
  const georssLayer = new google.maps.KmlLayer({
    url: "http://api.flickr.com/services/feeds/geo/?g=322338@N20&lang=en-us&format=feed-georss",
  });

  georssLayer.setMap(map);
}

window.initMap = 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>GeoRSS Layers</title>

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

    <!-- 
      The `defer` attribute causes the script to execute after the full HTML
      document has been parsed. For non-blocking uses, avoiding race conditions,
      and consistent behavior across browsers, consider loading using Promises. See
      https://developers.google.com/maps/documentation/javascript/load-maps-js-api
      for more information.
      -->
    <script
      src="https://maps.googleapis.com/maps/api/js?key=AIzaSyB41DRUbKWJHPxaFjMAwdrzWzbVKartNGg&callback=initMap&v=weekly"
      defer
    ></script>
  </body>
</html>

Попробуйте образец

В следующем примере создается объект KmlLayer из заданного KML-файла:

Машинопись

function initMap(): void {
  const map = new google.maps.Map(
    document.getElementById("map") as HTMLElement,
    {
      zoom: 11,
      center: { lat: 41.876, lng: -87.624 },
    }
  );

  const ctaLayer = new google.maps.KmlLayer({
    url: "https://googlearchive.github.io/js-v2-samples/ggeoxml/cta.kml",
    map: map,
  });
}

declare global {
  interface Window {
    initMap: () => void;
  }
}
window.initMap = initMap;

JavaScript

function initMap() {
  const map = new google.maps.Map(document.getElementById("map"), {
    zoom: 11,
    center: { lat: 41.876, lng: -87.624 },
  });
  const ctaLayer = new google.maps.KmlLayer({
    url: "https://googlearchive.github.io/js-v2-samples/ggeoxml/cta.kml",
    map: map,
  });
}

window.initMap = 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>KML Layers</title>

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

    <!-- 
      The `defer` attribute causes the script to execute after the full HTML
      document has been parsed. For non-blocking uses, avoiding race conditions,
      and consistent behavior across browsers, consider loading using Promises. See
      https://developers.google.com/maps/documentation/javascript/load-maps-js-api
      for more information.
      -->
    <script
      src="https://maps.googleapis.com/maps/api/js?key=AIzaSyB41DRUbKWJHPxaFjMAwdrzWzbVKartNGg&callback=initMap&v=weekly"
      defer
    ></script>
  </body>
</html>

Попробуйте образец

Подробная информация о возможностях KML

Поскольку KML-файл может содержать большое количество объектов, вы не можете получить прямой доступ к данным объектов из объекта KmlLayer . Вместо этого, по мере отображения объектов, они отображаются в виде кликабельных наложений Maps JavaScript API. По умолчанию щелчок по отдельным объектам открывает InfoWindow , содержащее информацию KML <title> и <description> о данном объекте. Кроме того, щелчок по KML-объекту генерирует событие KmlMouseEvent , которое передает следующую информацию:

  • position указывает координаты широты/долготы, к которым следует привязать InfoWindow для данного KML-объекта. Эта позиция обычно соответствует месту щелчка для полигонов, полилиний и наложений поверхности, но является истинной точкой отсчета для маркеров.
  • pixelOffset указывает смещение относительно указанной выше position для закрепления «хвоста» InfoWindow . Для многоугольных объектов это смещение обычно 0,0 , но для маркеров включает высоту маркера.
  • featureData содержит JSON-структуру KmlFeatureData .

Ниже представлен пример объекта KmlFeatureData :

{
  author: {
    email: "nobody@google.com",
    name: "Mr Nobody",
    uri: "http://example.com"
  },
  description: "description",
  id: "id",
  infoWindowHtml: "html",
  name: "name",
  snippet: "snippet"
}

В следующем примере при щелчке по объекту отображается текст <Description> из KML-файла внутри бокового блока <div> :

Машинопись

function initMap(): void {
  const map = new google.maps.Map(
    document.getElementById("map") as HTMLElement,
    {
      zoom: 12,
      center: { lat: 37.06, lng: -95.68 },
    }
  );

  const kmlLayer = new google.maps.KmlLayer({
    url: "https://raw.githubusercontent.com/googlearchive/kml-samples/gh-pages/kml/Placemark/placemark.kml",
    suppressInfoWindows: true,
    map: map,
  });

  kmlLayer.addListener("click", (kmlEvent) => {
    const text = kmlEvent.featureData.description;

    showInContentWindow(text);
  });

  function showInContentWindow(text: string) {
    const sidebar = document.getElementById("sidebar") as HTMLElement;

    sidebar.innerHTML = text;
  }
}

declare global {
  interface Window {
    initMap: () => void;
  }
}
window.initMap = initMap;

JavaScript

function initMap() {
  const map = new google.maps.Map(document.getElementById("map"), {
    zoom: 12,
    center: { lat: 37.06, lng: -95.68 },
  });
  const kmlLayer = new google.maps.KmlLayer({
    url: "https://raw.githubusercontent.com/googlearchive/kml-samples/gh-pages/kml/Placemark/placemark.kml",
    suppressInfoWindows: true,
    map: map,
  });

  kmlLayer.addListener("click", (kmlEvent) => {
    const text = kmlEvent.featureData.description;

    showInContentWindow(text);
  });

  function showInContentWindow(text) {
    const sidebar = document.getElementById("sidebar");

    sidebar.innerHTML = text;
  }
}

window.initMap = initMap;

CSS

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

#container {
  height: 100%;
  display: flex;
}

#sidebar {
  flex-basis: 15rem;
  flex-grow: 1;
  padding: 1rem;
  max-width: 30rem;
  height: 100%;
  box-sizing: border-box;
  overflow: auto;
}

#map {
  flex-basis: 0;
  flex-grow: 4;
  height: 100%;
}

HTML

<html>
  <head>
    <title>KML Feature Details</title>

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

    <!-- 
      The `defer` attribute causes the script to execute after the full HTML
      document has been parsed. For non-blocking uses, avoiding race conditions,
      and consistent behavior across browsers, consider loading using Promises. See
      https://developers.google.com/maps/documentation/javascript/load-maps-js-api
      for more information.
      -->
    <script
      src="https://maps.googleapis.com/maps/api/js?key=AIzaSyB41DRUbKWJHPxaFjMAwdrzWzbVKartNGg&callback=initMap&v=weekly"
      defer
    ></script>
  </body>
</html>

Попробуйте образец

Ограничения по размеру и сложности для рендеринга KML-файлов.

API JavaScript для работы с картами имеет ограничения по размеру и сложности загружаемых KML-файлов. Ниже приведено краткое описание текущих ограничений.

Примечание: Данные ограничения могут быть изменены в любое время.

Максимальный размер загружаемого файла (в формате KML, GeoRSS или KMZ в сжатом виде)
3 МБ
Максимальный размер несжатого KML-файла
10 МБ
Максимальный размер несжатого файла изображения в формате KMZ.
500 КБ на файл
Максимальное количество сетевых каналов
10
Максимальное общее количество функций, доступных в рамках всего документа.
1000
Количество слоев KML
Существует ограничение на количество KML-слоев, которые могут отображаться на одной карте Google. Если вы превысите этот лимит, ни один из ваших слоев не отобразится на карте, и в консоли JavaScript вашего веб-браузера будет сообщено об ошибке. Лимит основан на сочетании количества созданных классов KmlLayer и общей длины всех URL-адресов, используемых для создания этих слоев. Каждый новый созданный вами KmlLayer будет занимать часть лимита для слоя и дополнительную часть лимита в зависимости от длины URL-адреса, с которого был загружен KML-файл. Следовательно, количество слоев, которые вы можете добавить, будет варьироваться в зависимости от приложения; в среднем вы сможете загрузить от 10 до 20 слоев, не достигая лимита. Если вы все же достигли лимита, используйте сокращатель URL-адресов для сокращения URL-адресов KML-файлов. В качестве альтернативы создайте один KML-файл, состоящий из сетевых ссылок на отдельные URL-адреса KML-файлов.

Вопросы производительности и кэширования

Серверы Google будут временно кэшировать KML-файлы, чтобы снизить нагрузку на ваши серверы. Это также повысит производительность для ваших пользователей, предоставляя им компактное представление соответствующих сегментов вашего KML-файла по мере того, как пользователи будут щелкать по карте, перемещаться по ней и масштабировать её.

Для достижения наилучших результатов мы рекомендуем следующее:

  • Используйте соответствующий тег <expires> в KML.

    KmlLayer не будет использовать HTTP-заголовки при определении способа кэширования KML-файлов.
  • Не следует создавать файлы динамически во время выполнения запроса.

    Вместо этого сгенерируйте файлы заранее, до того, как они понадобятся, и разместите их статически. Если вашему серверу потребуется много времени для передачи KML-файла, KmlLayer может не отобразиться.
  • Не пытайтесь обойти кэш, если вы точно не знаете, что ваш файл был обновлен.

    Постоянное игнорирование кэша (например, путем добавления случайного числа или времени пользователя в качестве параметра запроса) может легко привести к перегрузке ваших серверов, если ваш сайт внезапно станет популярным, и вы будете обслуживать большие KML-файлы.

    Это также может привести к тому, что кэш будет предоставлять пользователям устаревшие данные, если время какого-либо пользователя установлено неверно, а тег <expires> не был установлен корректно.

    Вместо этого публикуйте обновленные статические файлы с новым, отдельным номером ревизии и используйте серверный код для динамического обновления URL-адреса, передаваемого в KmlLayer с указанием текущей версии.
  • Ограничьте внесение изменений в KML-файлы до одного раза в минуту.

    Если общий размер всех файлов превышает 1 МБ (в несжатом виде), ограничьте внесение изменений до одного раза в 5 минут.
  • При использовании сервера геопространственных данных избегайте использования параметров запроса для ограничения области просмотра слоев.

    Вместо этого вы можете ограничить область просмотра карты с помощью события bounds_changed . Пользователям будут отправляться только те объекты, которые могут отображаться автоматически.

    Если на вашем сервере геопространственных данных хранится большой объем информации, рассмотрите возможность использования слоев данных .
  • При использовании сервера геопространственных данных используйте несколько KmlLayer для каждой группы объектов, которые вы хотите разрешить пользователям переключать, вместо одного KmlLayer с различными параметрами запроса.
  • Используйте сжатые KMZ-файлы для уменьшения размера файла.
  • Если вы используете Google Cloud Storage или другое облачное хранилище, избегайте использования таких функций, как подписанные URL-адреса или временные токены для обеспечения контроля доступа. Это может непреднамеренно препятствовать кэшированию.
  • Уменьшите точность всех точек до соответствующего уровня .
  • Объединять и упрощать геометрию похожих объектов, таких как многоугольники и ломаные линии.
  • Удалите все неиспользуемые элементы или графические ресурсы.
  • Удалите все неподдерживаемые элементы .

Если вам необходимо получить доступ к конфиденциальным данным, предотвратить кэширование или передать область просмотра браузера на сервер геопространственных данных в качестве параметра запроса, мы рекомендуем использовать слои данных вместо KmlLayer . Это направит браузеры ваших пользователей напрямую запрашивать ресурсы с вашего веб-сервера.

Поддерживаемые элементы KML

API JavaScript для работы с картами поддерживает следующие элементы KML. Парсер KML, как правило, молча игнорирует XML-теги, которые он не понимает.

  • Метки мест
  • Иконки
  • Папки
  • Описательный HTML — замена сущностей с помощью <BalloonStyle> и <text>
  • KMZ (сжатый KML, включая прикрепленные изображения)
  • Полилинии и многоугольники
  • Стили для полилиний и полигонов, включая цвет, заливку и прозрачность.
  • Сетевые ссылки для динамического импорта данных
  • Напольные покрытия и экранирующие покрытия

В таблице ниже приведена полная информация о поддерживаемых элементах KML.

элемент KML Поддерживается ли это в API? Комментарий
<адрес> нет
<AddressDetails> нет
<Псевдоним> Н/Д <Модель> не поддерживается
<высота> нет
<altitudeMode> нет
<atom:author> да
<atom:link> да
<atom:name> да
<BalloonStyle> частично Поддерживается только <текст>
<begin> Н/Д <TimeSpan> не поддерживается
<bgColor> нет
<bottomFov> Н/Д Функция <PhotoOverlay> не поддерживается.
<Камера> нет
<Изменить> частично Поддерживаются только изменения стиля.
<цвет> частично включает #AABBGGRR и #BBGGRR; не поддерживается в <IconStyle>, <ScreenOverlay> и <GroundOverlay>.
<colorMode> нет
<cookie> нет
<координаты> да
<Создать> нет
<Данные> да
<Удалить> нет
<описание> да HTML-контент разрешен, но проходит проверку на безопасность для защиты от межбраузерных атак. Замена сущностей в формате $[ dataName ] не поддерживается.
<displayMode> нет
<displayName> нет
<Документ> частично По сути, детям оказывается поддержка; это не оказывает никакого влияния на детей, являющихся детьми других особенностей.
<drawOrder> нет
<восток> да
<конец> Н/Д <TimeSpan> не поддерживается
<срок действия> да Подробности см. в разделе «Краткое описание».
<ExtendedData> частично Поддерживается только нетипизированный <Data>, не поддерживаются <SimpleData> или <Schema>, а также замена сущностей в формате $[ dataName ] .
<выдавливание> нет
<заполнить> да
<flyToView> нет
<Папка> да
<geomColor> нет устаревший
<GeometryCollection> нет устаревший
<geomScale> нет устаревший
<gridOrigin> Н/Д Функция <PhotoOverlay> не поддерживается.
<GroundOverlay> да не может быть повернут
<h> да устаревший
<заголовок> да
намекать да target=... поддерживается
<hotSpot> да
<href> да
<httpQuery> нет
<Иконка> да не может быть повернут
<IconStyle> да
<ImagePyramid> Н/Д Функция <PhotoOverlay> не поддерживается.
<innerBoundaryIs> да неявно из порядка <LinearRing>
<ItemIcon> Н/Д <ListStyle> не поддерживается
<ключ> Н/Д <StyleMap> не поддерживается
<kml> да
<labelColor> нет устаревший
<LabelStyle> нет
<широта> да
<LatLonAltBox> да
<LatLonBox> да
<leftFov> Н/Д Функция <PhotoOverlay> не поддерживается.
<LinearRing> да
<LineString> да
<LineStyle> да
<Ссылка> да
<linkDescription> нет
<linkName> нет
<linkSnippet> нет
<listItemType> Н/Д <ListStyle> не поддерживается
<ListStyle> нет
<Местоположение> Н/Д <Модель> не поддерживается
<Лод> да
<долгота> да
<Посмотрите> нет
<maxAltitude> да
<maxFadeExtent> да
<maxHeight> Н/Д Функция <PhotoOverlay> не поддерживается.
<maxLodPixels> да
<maxSessionLength> нет
<maxWidth> Н/Д Функция <PhotoOverlay> не поддерживается.
<сообщение> нет
<Метаданные> нет устаревший
<минимальная высота> да
<minFadeExtent> да
<minLodPixels> да
<minRefreshPeriod> нет <NetworkLink>
<Модель> нет
<МультиГеометрия> частично Отображаются, но отображаются как отдельные элементы на левой боковой панели.
<имя> да
<рядом> Н/Д Функция <PhotoOverlay> не поддерживается.
<NetworkLink> да
<NetworkLinkControl> частично Частично поддерживаются параметры <Update> и <expires>. API игнорирует настройки истечения срока действия в заголовках HTTP, но использует настройки истечения срока действия, указанные в KML. В отсутствие настроек истечения срока действия или в течение установленного интервала действия Google Maps может кэшировать данные, полученные из Интернета, на неопределенный срок. Повторную загрузку данных из Интернета можно принудительно выполнить, переименовав документ и загрузив его по другому URL-адресу, или убедившись, что документ содержит соответствующие настройки истечения срока действия.
<север> да
<открыть> да
<Ориентация> Н/Д <Модель> не поддерживается
<outerBoundaryIs> да неявно из порядка <LinearRing>
<контур> да
<overlayXY> нет
<Пара> Н/Д <StyleMap> не поддерживается
<номер телефона> нет
<PhotoOverlay> нет
<Метка> да
<Точка> да
<Многоугольник> да
<PolyStyle> да
<диапазон> да
<refreshInterval> частично Только <ссылка>; не в <значке>
<refreshMode> да HTTP-заголовки не поддерживаются в режиме "onExpire". См. примечания к <Update> и <expires> выше.
<refreshVisibility> нет
<Регион> да
<Карта ресурсов> Н/Д <Модель> не поддерживается
<rightFov> Н/Д Функция <PhotoOverlay> не поддерживается.
<ролл> Н/Д <Камера> и <Модель> не поддерживаются.
<вращение> нет
<rotationXY> нет
<Масштаб> Н/Д <Модель> не поддерживается
<масштаб> нет
<Схема> нет
<SchemaData> нет
<ScreenOverlay> да не может быть повернут
<screenXY> нет
<форма> Н/Д Функция <PhotoOverlay> не поддерживается.
<SimpleData> Н/Д <SchemaData> не поддерживаются
<SimpleField> Н/Д <Схемы> не поддерживаются
<размер> да
<Фрагмент> да
<юг> да
<штат> Н/Д <ListStyle> не поддерживается
<Стиль> да
<Карта стилей> нет Эффекты наведения курсора (подсветки) не поддерживаются.
<styleUrl> Н/Д <StyleMap> не поддерживается
<targetHref> частично Поддерживается в <Update>, но не в <Alias>.
<тесселят> нет
<текст> да Замена $[geDirections] не поддерживается.
<textColor> нет
<tileSize> Н/Д Функция <PhotoOverlay> не поддерживается.
<наклон> нет
<TimeSpan> нет
<Временная метка> нет
<topFov> Н/Д Функция <PhotoOverlay> не поддерживается.
<Обновление> частично Изменения касаются только стиля, а не функций <Создать> или <Удалить>.
<Url> да устаревший
<value> да
<viewBoundScale> нет
<viewFormat> нет
<viewRefreshMode> частично Функция «onStop» поддерживается.
<viewRefreshTime> да
<ViewVolume> Н/Д Функция <PhotoOverlay> не поддерживается.
<видимость> частично Да, папка <Folder> — дочерние метки наследуют свою видимость.
<w> да устаревший
<запад> да
<когда> Н/Д <TimeStamp> не поддерживается
<ширина> да
<x> да устаревший
<y> да устаревший