简体   繁体   中英

How to draw direction between two points using ( react-google-maps ) in ReactJS?

I am using the react-google-maps library to set a map. I have set a map and markers correctly but I don't know how to draw a route between two points means starting point to the destination point.

I am new in react and I am trying to learn things if anyone can help please help me to solve this problem!

I used skateboard-parks.json for markers.

RoutePlan.js


import React, { memo, useState, useEffect, useCallback } from "react";
import PropTypes from "prop-types";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
import { compose } from "redux";

import { useInjectSaga } from "utils/injectSaga";
import { useInjectReducer } from "utils/injectReducer";
import makeSelectRoutePlan from "./selectors";
import reducer from "./reducer";
import FaisalMosque from '../../components/Mosque/Mosque';
import MosqueChange from '../../components/Mosque/MosqueChange';
import Bed from '../../components/Bed/Bed';
import BedChange from '../../components/Bed/BedChange';
import HorseRiding from '../../components/HorseRiding/HorseRiding';
import HorseRidingChange from '../../components/HorseRiding/HorseRidingChange';
import saga from "./saga";
import '../../../styles/main.css';
import Button from '../../components/Button/index'
import { Form, Col } from 'react-bootstrap';
import {
  withGoogleMap,
  withScriptjs,
  GoogleMap,
  Marker,
  InfoWindow
} from "react-google-maps";
import * as parkData from "./data/skateboard-parks.json";


function Map() {
  const [selectedPark, setSelectedPark] = useState(null);

  const Points = [
            { startingPoint: 'Los Angles', destinationPoint: 'Chicago'},
       ]

  useEffect(() => {
    const listener = e => {
      if (e.key === "Escape") {
        setSelectedPark(null);
      }
    };
    window.addEventListener("keydown", listener);

    return () => {
      window.removeEventListener("keydown", listener);
    };
  }, []);

  return (
    <GoogleMap
      defaultZoom={8}
      defaultCenter={{ lat: 45.4211, lng: -75.6903 }}
    >
      {parkData.features.map(park => (
        <Marker
          key={park.properties.PARK_ID}
          position={{
            lat: park.geometry.coordinates[1],
            lng: park.geometry.coordinates[0]
          }}
          onClick={() => {
            setSelectedPark(park);
          }}
        />
      ))}

      {selectedPark && (
        <InfoWindow
          onCloseClick={() => {
            setSelectedPark(null);
          }}
          position={{
            lat: selectedPark.geometry.coordinates[1],
            lng: selectedPark.geometry.coordinates[0]
          }}
        >
          <div>
            <h2>{selectedPark.properties.NAME}</h2>
            <p>{selectedPark.properties.DESCRIPTIO}</p>
          </div>
        </InfoWindow>
      )}
    </GoogleMap>
  );
}

const MapWrapped = withScriptjs(withGoogleMap(Map));

export function RoutePlan() {
  useInjectReducer({ key: "routePlan", reducer });
  useInjectSaga({ key: "routePlan", saga });


return (
    <div>
      <div className="page-content-wrapper py-1">
        <div className="container">
    
          <div style={{ width: "auto", height: "500px", borderRadius: "20px" }}>
            <MapWrapped
              googleMapURL={"https://maps.googleapis.com/maps/api/js?key=AIzaSyBKG4NZAluyN8b-1rBsDWc9bQl1Z0KUxwg&v=3.exp&libraries=geometry,drawing,places"}
              loadingElement={<div style={{ height: `100%`, borderRadius: `20px` }} />}
              containerElement={<div style={{ height: `100%`, borderRadius: `20px` }} />}
              mapElement={<div style={{ height: `100%`, borderRadius: `20px` }} />}
            />
          </div>

  </div>
      </div>
    </div>


  );
}


RoutePlan.propTypes = {
  dispatch: PropTypes.func.isRequired
};

const mapStateToProps = createStructuredSelector({
  routePlan: makeSelectRoutePlan()
});

function mapDispatchToProps(dispatch) {
  return {
    dispatch
  };
}

const withConnect = connect(
  mapStateToProps,
  mapDispatchToProps
);

export default compose(
  withConnect,
  memo
)(RoutePlan);


skateboard-parks.json


{
  "type": "FeatureCollection",
  "crs": {
    "type": "name",
    "properties": { "name": "urn:ogc:def:crs:OGC:1.3:CRS84" }
  },
  "features": [
    {
      "type": "Feature",
      "properties": {
        "PARK_ID": 960,
        "FACILITYID": 28014,
        "NAME": "Bearbrook Skateboard Park",
        "NAME_FR": "Planchodrome Bearbrook",
        "ADDRESS": "8720 Russell Road",
        "ADDRESS_FR": "8720, chemin Russell",
        "FACILITY_T": "flat",
        "FACILITY_1": "plat",
        "ACCESSCTRL": "no/non",
        "ACCESSIBLE": "no/non",
        "OPEN": null,
        "NOTES": "Outdoor",
        "MODIFIED_D": "2018/01/18",
        "CREATED_DA": null,
        "FACILITY": "Neighbourhood : smaller size facility to service population of 10,000 or less",
        "FACILITY_F": "De voisinage : petite installation assurant des services à 10 000 résidents ou moins.",
        "DESCRIPTIO": "Flat asphalt surface, 5 components",
        "DESCRIPT_1": "Surface d'asphalte plane, 5 modules",
        "PICTURE_LI": null,
        "PICTURE_DE": null,
        "PICTURE__1": null
      },
      "geometry": {
        "type": "Point",
        "coordinates": [-75.3372987731628, 45.383321536272049]
      }
    },
    {
      "type": "Feature",
      "properties": {
        "PARK_ID": 1219,
        "FACILITYID": 28001,
        "NAME": "Bob MacQuarrie Skateboard Park (SK8 Extreme Park)",
        "NAME_FR": "Planchodrome Bob-MacQuarrie (Parc SK8 Extreme)",
        "ADDRESS": "1490 Youville Drive",
        "ADDRESS_FR": "1490, promenade Youville",
        "FACILITY_T": "other",
        "FACILITY_1": "autre",
        "ACCESSCTRL": "no/non",
        "ACCESSIBLE": "no/non",
        "OPEN": null,
        "NOTES": "Outdoor",
        "MODIFIED_D": "2018/01/18",
        "CREATED_DA": null,
        "FACILITY": "Community: mid size facility to service population of 40,000 plus",
        "FACILITY_F": "Communautaire : installation de taille moyenne assurant des services à 40 000 résidents ou plus.",
        "DESCRIPTIO": "Flat asphalt surface, 10 components, City run learn to skateboard programs, City run skateboard camps in summer",
        "DESCRIPT_1": "Surface d'asphalte plane, 10 modules, programmes et camps de planche à roulettes en été géré par la Ville",
        "PICTURE_LI": null,
        "PICTURE_DE": null,
        "PICTURE__1": null
      },
      "geometry": {
        "type": "Point",
        "coordinates": [-75.546518086577947, 45.467134581917357]
      }
    },
    {
      "type": "Feature",
      "properties": {
        "PARK_ID": 2278,
        "FACILITYID": 49211,
        "NAME": "Vista Skateboard Park",
        "NAME_FR": "Planchodrome Vista",
        "ADDRESS": "720 Vistapark Drive",
        "ADDRESS_FR": "720, promenade Vistapark",
        "FACILITY_T": "flat",
        "FACILITY_1": "plat",
        "ACCESSCTRL": "no/non",
        "ACCESSIBLE": "yes/oui",
        "OPEN": null,
        "NOTES": "Outdoor",
        "MODIFIED_D": "2018/11/29",
        "CREATED_DA": "2018/06/22",
        "FACILITY": "Neighbourhood : smaller size facility to service population of 10,000 or less",
        "FACILITY_F": "De voisinage : petite installation assurant des services à 10 000 résidents ou moins.",
        "DESCRIPTIO": "Flat surface, 5 components",
        "DESCRIPT_1": "Surface plane, 5 modules",
        "PICTURE_LI": null,
        "PICTURE_DE": null,
        "PICTURE__1": null
      },
      "geometry": {
        "type": "Point",
        "coordinates": [-75.471003922143311, 45.450391044010431]
      }
    },
    {
      "type": "Feature",
      "properties": {
        "PARK_ID": 2113,
        "FACILITYID": 35299,
        "NAME": "Innovation Skateboard Park",
        "NAME_FR": "Planchomdrome Innovation",
        "ADDRESS": "4101 Innovation Drive",
        "ADDRESS_FR": "4101, promenade Innovation",
        "FACILITY_T": "bowl",
        "FACILITY_1": "bol",
        "ACCESSCTRL": "no/non",
        "ACCESSIBLE": "yes/oui",
        "OPEN": null,
        "NOTES": "Outdoor",
        "MODIFIED_D": "2017/07/11",
        "CREATED_DA": "2016/02/08",
        "FACILITY": "District: larger facility to service population of 100,000 plus",
        "FACILITY_F": "De district : grande installation assurant des services à 100 000 résidents ou plus.",
        "DESCRIPTIO": "Large concrete bowl, 10 plus components, many street and vertical components",
        "DESCRIPT_1": "Grand bol de béton, 10 modules ou plus, modules de rue et modules verticaux",
        "PICTURE_LI": null,
        "PICTURE_DE": null,
        "PICTURE__1": null
      },
      "geometry": {
        "type": "Point",
        "coordinates": [-75.931122879767898, 45.34125624499935]
      }
    }
  ]
}


There's a DirectionsRenderer in react-google-maps which you can use to call a Directions API request by passing your origin, destination etc. to DirectionsService then invoke DirectionsRenderer to display the route in the map.

Additionally, you can also check the @react-google-maps/api library as this is complete re-write of the (sadly unmaintained) react-google-maps library.

Here's a sample code and code snippet below:

/*global google*/
import ReactDOM from "react-dom";
import React from "react";

import { GoogleMap, DirectionsRenderer } from "@react-google-maps/api";

const defaultLocation = { lat: 40.756795, lng: -73.954298 };
let destination = { lat: 41.756795, lng: -78.954298 };
let origin = { lat: 40.756795, lng: -73.954298 };
let directionsService;
class Map extends React.Component {
  state = {
    directions: null,
    bounds: null
  };

  onMapLoad = map => {
    directionsService = new google.maps.DirectionsService();
    //load default origin and destination
    this.changeDirection(origin, destination);
  };

  //function that is calling the directions service
  changeDirection = (origin, destination) => {
    directionsService.route(
      {
        origin: origin,
        destination: destination,
        travelMode: google.maps.TravelMode.DRIVING
      },
      (result, status) => {
        if (status === google.maps.DirectionsStatus.OK) {
          //changing the state of directions to the result of direction service
          this.setState({
            directions: result
          });
        } else {
          console.error(`error fetching directions ${result}`);
        }
      }
    );
  };

  render() {
    return (
      <div>
        <GoogleMap
          center={defaultLocation}
          zoom={5}
          onLoad={map => this.onMapLoad(map)}
          mapContainerStyle={{ height: "400px", width: "800px" }}
        >
          {this.state.directions !== null && (
            <DirectionsRenderer directions={this.state.directions} />
          )}
        </GoogleMap>
      </div>
    );
  }
}

export default Map;

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM