Add a React component to the information window of Google Maps

I have successfully integrated multiple markers on a Google Map. Now, I am looking to add specific content for each marker. While coding everything in strings works fine, I encountered an issue when trying to load React elements inside those strings.

For this project, we are utilizing IconUiKit to showcase icons. The objective is to include a pin icon within the info window.

I came across a similar question to mine here => How to use a react component for showing Google Maps InfoWindow. However, I faced an error indicating that ReactDOMServer could not be found while using ReactDOMServer.renderToString().

private setMarkers(map: any): any {
  const {stores} = this.state;
  const infowindow = new google.maps.InfoWindow({
    maxWidth: 400
  });
  for (let i = 0; i < stores.length; i++) {  
    if (google.maps.GeocoderStatus.OK === 'OK' && stores[i].store.address && 
       (Number(stores[i].store.address.latitude) !== undefined) && 
       Number(stores[i].store.address.longitude)) {
      let lat = stores[i].store.address.latitude !== undefined ? stores[i].store.address.latitude : 0;
      let lng = stores[i].store.address.longitude !== undefined ? stores[i].store.address.longitude : 0;
      let pos = lat && lng ? new google.maps.LatLng(lat, lng) : {lat: 0, lng: 0};

      let marker = new google.maps.Marker({
        map: map,
        position: pos
      });

      let projectInfo = [] as string[];
      stores[i].projects.forEach(project => {
        projectInfo.push(
          `<p><b>${project.projectNo}</b></p>` +
          '<p>Attribution: Uluru,' + 
            '<a href="https://en.wikipedia.org/w/index.php?title=Uluru&oldid=297882194">' +
              'https://en.wikipedia.org/w/index.php?title=Uluru' + 
            '</a>' +
          '(last visited June 22, 2009).</p>' +
          '<a class="uk-button uk-button-grey uk-button-register uk-width-1-1 uk-text-uppercase" href="/">' +
            '<span>' +
              'Project Details' +
            '</span>' +
          '</a>'
        );
      });
      let icon = <IconUikit icon="gear" wrap={true}/>;
      console.log(icon.toString());

      let contentString = 
        '<div class="maps-tooltip">' +
          '<div class="uk-grid">' +
            '<div class="uk-width-1-4">' +
              `<img src="${stores[i].store.imageUrl}" class="uk-width-1-1"/>` +
            '</div>' +
            '<div class="uk-width-3-4">' +
              `<p><b class="fr-color-black">${stores[i].store.address.name1}</b></p>` +
               /// REPLACE WITH YOUR COMPONENT HERE
              ReactDOMServer.renderToString(<IconUikit icon="gear" wrap={true}/>) +
            '</div>' +
            '<div class="uk-width-1-1">' +
              `${projectInfo.toString()}` +
            '</div>' +
          '</div>' +
        '</div>';

      google.maps.event.addListener(marker, 'click', function() {
        infowindow.setOptions({
          content: contentString,
        });
        infowindow.open(map, marker);
      });
    }
  }
}

Answer №1

Issue Resolved!

A helpful solution was provided for the problem with ReactDomServer - make sure to include { renderToString } from 'react-dom/server' instead of calling ReactDomServer.renderToString(). This should resolve the issue.

Answer №2

Marlon Berdefy provided the correct answer above. Let's further explain it with an example:

To utilize Google Maps InfoWindow component, you must provide it with a string in the content. You can incorporate a component by using renderToString and enclosing it in brackets: ${ButtonToString}

` import { Button } from 'rsuite'; import { renderToString } from 'react-dom/server';

const ButtonToString = renderToString(Register).toString()

let marker;
let content;
// The marker is placed at Uluru
for(let i = 0; i < host.length; i++) {
  const markerPosition = { lat: host[i].lat, lng: host[i].lng };
  marker = new AdvancedMarkerElement({
    map: map,
    position: markerPosition,
    title: host[i].foodType,
  });

  content = 
  `<div className="flex flex-col text-gray-600">` +
    `<div className="text-lg font-bsold">${host[i].foodType}</div>` +
    `<div className="mt-2">` +
      `<div className="flex items-center">` +
        `<span>${host[i].description}</span>` +
      `</div>` +
      `<div className="flex items-center mt-1">` +
        `<div>Guest spots left: <span className="font-bold">${host[i].guestSpotsLeft}</span></div>` +
      `</div>` +
      `<div className="flex items-center mt-1">` +
        `<div className="font-bold">$${host[i].price} per person</div>` +
      `</div>` +
    `</div>` +
    `<div className='flex justify-end'>` +
      `${ButtonToString}` +
    `</div>` +
  `</div>`

`

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

I encounter difficulties in executing a request through ReactJS, as the header cannot be properly composed

const fetchData = async () => { try { const response = await axios.get('http://localhost:8080/omp/patients', { headers: {authorization: 'Bearer ' + token}}); this.state = response.data; } catch (ex) { ...

Exploring URL Parameters in Angular Unit Testing

My goal is to execute a test to check for the presence of a specific string in URL parameters. Inside my TypeScript file, I have defined the following method: checkURLParams() { if (this.route.parent) { this.route.parent.params.subscribe((params) ...

Implementing Dynamic Component Rendering in React Native with Typescript

For the past 3 hours, I've been grappling with this particular issue: const steps = [ { Component: ChooseGameMode, props: { initialValue: gameMode, onComplete: handleChooseGameModeComplete } }, { Com ...

The FileSaver application generates a unique file with content that diverges from the original document

I'm attempting to utilize the Blob function to generate a file from information transmitted via a server call, encoded in base64. The initial file is an Excel spreadsheet with a length of 5,507 bytes. After applying base64 encoding (including newlines ...

How can I prevent my mouse click from being overridden by my mouse hover?

Currently, I am developing a Sudoku game using JavaScript and facing some challenges with mouse events. My goal is to enable users to hover over a square and have it change color, as well as click on a square to highlight the entire row, column, and quadra ...

How can we validate the radio buttons to show a value even if none of the buttons are checked?

In my registration form, I have a gender radio option with "male" or "female" choices. Both options are unchecked initially so the user must select one. Here is the HTML code: <label class="radio"> <input type="radio" name="gender" id="option ...

What's the best way to place my image inside a Bootstrap Accordion so that it is housed within the accordion-item?

I've been facing an issue with a Bootstrap Accordion. Everything works fine, except when I try to insert an image <img src="https://placehold.co/600x400" class="img-fluid" /> into an accordion-item <div class="accord ...

How to allow users to input strings on web pages with JavaScript

I created a Language Translator using java script that currently translates hardcoded strings in an HTML page. I want to enhance its flexibility by allowing users to input a string into a textbox/textarea for translation. Any assistance would be greatly a ...

Choose a row by selecting the checkbox in the Kendo UI grid using TypeScript

I'm just starting out with Kendo UI and Angular 2, and I'm currently working on integrating Kendo UI with Angular 2. Specifically, I have a Grid Module set up with checkboxes in each row. My goal is to extract the row ID or any other field value ...

Updating React Form State with Redux Props

I have a custom component that receives data from its parent using Redux. This component is responsible for managing a multistep form, allowing users to go back and update input fields in previous steps. However, I'm facing an issue with clearing out ...

Problem encountered when trying to show the Jquery Ajax response on an HTML page

I'm facing a challenge with loading a page that needs to display values with dynamic pagination. To retrieve these values, I am making a REST call which returns a JSON object. Although I can see the JSON output in the browser console, I am unable to d ...

Error: Running the command 'yarn eg:'live-server'' is not a valid internal or external command

Currently, I am utilizing yarn v1.6.0 to manage dependencies. I have globally installed live-server by running the following command: yarn global-add live-server However, upon executing it as live server, I encounter the following error: 'live-ser ...

Turn off the background when the automatic popup box appears

I have implemented a popup box that automatically appears after 5 seconds when the site is loaded. However, if I click outside of the popup box, it closes. I want to disable the background when the popup box is displayed. If I remove the two lines of code ...

Issue with displaying Bootstrap Tooltip

Recently, I launched a fresh website (currently residing on a sub-domain). However, I am facing an issue with the tooltip not showing up when hovering over the text Get the FinEco Bookmarklet. <span class="bookmarklet"><span class="fa fa-bookmark ...

What is the best way to display only a specific container from a page within an IFRAME?

Taking the example into consideration: Imagine a scenario where you have a webpage containing numerous DIVs. Now, the goal is to render a single DIV and its child DIVs within an IFrame. Upon rendering the following code, you'll notice a black box ag ...

What is the best way to choose a specific row with Enzyme?

We have chosen Jest for doing UI Test-Driven Development on our React application. Our component rendering structure looks like this: <Div> <Row> </Row> <ROW> <Row> <ROW> <Link> <Link> ...

Tips for monitoring changes to files while developing a NestJs application within a Docker container

Having an issue with NestJS and Docker here. Trying to run the development script using npm start: dev, but encountering a problem where the app runs fine but doesn't detect any changes in the source files, hindering the development process. Here&apo ...

Allow only specific inner divs to dictate the width of the outer div

I'm working with the following HTML structure: <div id="container"> <div id="block1"> <img src="someimage/path" /> </div> <div id="block2"> Some Text </div> <div id="block3"&g ...

Tips for disabling Hot Module Reloading in NextJS

In my project built with ReactJS and NextJS, users can upload their pictures, manipulate faces, and animate them. However, we are facing an issue where the page automatically reloads due to HMR (Hot Module Replacement), causing all user data to be lost. ...

Attempting to replicate the flipping motion of a card by applying the transform property to rotate a div element, ultimately revealing a different

I am attempting to create a series of divs that simulate the flipping action of a notecard. Unfortunately, when I hover over the div, it turns white because I have set the display property to none. I am unsure how to make the other div (.back) visible. Y ...