Внешний скрипт ReactJs - Карты Google

Я пытаюсь добавить Google Maps в веб-приложение ReactJs, но безуспешно.

Я знаю, что есть некоторые реагирующие компоненты, которые обертывают карты Google, но они не соответствуют моим реальным потребностям, поэтому мне приходится создавать их сам. Моя проблема в том, что я не знаю, как обрабатывать тег скрипта, необходимый для работы карт Google: <script src = "https://maps.googleapis.com/maps/api/js?key=AIzaSyD6maRCH9aI1K0sWA_FRdjIQv9AJgP7aQ0&callback=initMap" async defer></script>

Сначала я помещаю его в index.html, но получаю эту ошибку, когда запускаю приложение в chrome devtools:

Uncaught (in promise) 
Hc {message: "initMap is not a function", name: "InvalidValueError", stack: "Error↵    at new Hc (https://maps.googleapis.com/m…I1K0sWA_FRdjIQv9AJgP7aQ0&callback=initMap:124:108"}

Я пробовал использовать fetch(), чтобы получить сценарий, посмотреть, что это на самом деле, но он запрашивает заголовок CORS и думает, что я не знаю точных параметров, которые ожидает этот запрос, я думаю, что это не решение.

Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
0
0
1 074
2

Ответы 2

Причина, по которой вы получаете initMap, не является функцией, потому что помимо src скрипта, который вы указали в конце, является callback = initMap. Это запустит функцию под названием initMap после того, как скрипт завершит загрузку.

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

https://developers.google.com/maps/documentation/javascript/tutorial

Как сказал @Naismith, ошибка связана с callback=initMap в вашем скрипте Google Maps. Итак, чтобы это работало, вам нужно будет реализовать функцию initMap следующим образом:

<div id = "map"></div>
    <script>
      var map;
      function initMap() {
        map = new google.maps.Map(document.getElementById('map'), {
          center: {lat: -34.397, lng: 150.644},
          zoom: 8
        });
      }
    </script>
    <script src = "https://maps.googleapis.com/maps/api/js?key=YOUR_API_KEY&callback=initMap"
    async defer></script>

За исключением того, что вы пытаетесь отобразить карты в компоненте, в этом случае вы можете попробовать этот подход, при котором вы создаете обещание для API Карт Google и разрешаете это обещание в (глобальной) функции обратного вызова, которую может запустить API Карт Google. Затем в коде вашего компонента вы должны дождаться выполнения обещания, прежде чем продолжить.

class Map extends React.Component {
  getGoogleMaps() {
    if (!this.googleMapsPromise) {
      this.googleMapsPromise = new Promise((resolve) => {
        // Add a global handler for when the API finishes loading
        window.resolveGoogleMapsPromise = () => {
          // Resolve the promise
          resolve(google);

          // Tidy up
          delete window.resolveGoogleMapsPromise;
        };

        // Load the Google Maps API
        const script = document.createElement("script");
        const API = 'AIzaSyDbAz1XXxDoKSU2nZXec89rcHPxgkvVoiw';
        script.src = `https://maps.googleapis.com/maps/api/js?key=${API}&callback=resolveGoogleMapsPromise`;
        script.async = true;
        document.body.appendChild(script);
      });
    }

    // Return a promise for the Google Maps API
    return this.googleMapsPromise;
  }

  componentWillMount() {
    // Start Google Maps API loading since we know we'll soon need it
    this.getGoogleMaps();
  }

  componentDidMount() {
    // Once the Google Maps API has finished loading, initialize the map
    this.getGoogleMaps().then((google) => {
      const uluru = {lat: -25.366, lng: 131.044};
      const map = new google.maps.Map(document.getElementById('map'), {
        zoom: 4,
        center: laos
      });
      const marker = new google.maps.Marker({
        position: laos,
        map: map
      });
    });
  }

  render() {
    return (
      <div>
        <div id = "map" style = {{width: 600, height: 300}}></div>
      </div>
    )
  }
}

ReactDOM.render(
  <Map/>,
  document.getElementById('react')
);

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

Adrian Pascu 06.11.2018 19:51

Другие вопросы по теме