我开发了一个日托应用程序,所以我想在谷歌 map 上显示日托位置.我将Google Maps与React应用程序集成.加载应用程序时,它正确地显示了位置.但是,当拖动或zoom 时,我的位置也会移动.位置应该始终保持不变.我使用node.js express作为后端

Here's a video of the issue

https://app.screencastify.com/v3/watch/DltGBIYDwrZY0xlJw6v9

This is my code

import React, { useState, useEffect } from "react";
import GoogleMapReact from 'google-map-react';
import { Icon } from "@iconify/react";
import locationIcon from "@iconify/icons-mdi/map-marker";

const LocationPin = ({ name }) => (
    <div className="pin">
        <Icon icon={locationIcon} className="pin-icon" />
        <p className="pin-text">{name}</p>
    </div>
);

const Map = ({ daycares }) => {
    const [latitude, setLatitude] = useState(43.77887);
    const [longitude, setLongitude] = useState(-79.17282);

    useEffect(() => {
        navigator.geolocation.getCurrentPosition(
            (position) => {
                setLatitude(position.coords.latitude);
                setLongitude(position.coords.longitude);
            },
            (error) => {
                console.error(error);
            }
        );
    }, []); // Empty dependency array means this effect runs only once after the initial render

    const renderMap = () => {
        if (!daycares || daycares.length === 0) {
            return null; // Return early if daycares is empty or undefined
        }

        return (
            <div style={{ height: "80vh", width: "100%" }}>
                <GoogleMapReact
                    bootstrapURLKeys={{ key: "AIzaSyAzEQgX_hi-_Qnv6aWWIQDAdcLYnFPqQSQ" }}
                    defaultCenter={{
                        lat: latitude,
                        lng: longitude
                    }}
                    defaultZoom={12}
                >
                    {daycares.map((daycare) => (
                        <LocationPin
                            key={daycare.id}
                            lat={parseFloat(daycare.latitude)}
                            lng={parseFloat(daycare.longitude)}
                            name={daycare.childcare_name}
                        />
                    ))}
                </GoogleMapReact>
            </div>
        );
    };

    return (
        <div>
            {renderMap()}
        </div>
    );
};

export default Map;

const LocationPin = ({ lat, lng, name }) => (
  <div className="pin" style={{ position: 'absolute', transform: 'translate(-50%, -50%)' }}>
    <Icon icon={locationIcon} className="pin-icon" />
    <p className="pin-text">{name}</p>
  </div>
);

export default LocationPin;

位置应该始终保持不变

我的模拟数据:

{
  childcare_name: "East Side Preschool",
  address: "458 Fairall Street",
  city: "Ajax",
  region: "Ontario",
  postalcode: " L1S 1R6",
  country: "CANADA",
  latitude: "43.75991",
  longitude: "-79.18827",
  owner_name: "Jessica Lee",
  age_range: "2-6",
  years: "4",
  infant_capacity: "8",
  toddler_capacity: "12",
  preschool_capacity: "18",
  contact_phone: "555-9012",
  contact_email: "jessica@example.com",
},
{
  childcare_name: "Kepalen Angelic Child Care Daycare",
  address: "1301 Neilson Rd",
  city: "Scarborough",
  region: "Ontario",
  postalcode: "M1B 3C2",
  country: "Canada",
  latitude: "43.80716",
  longitude: "-79.21856",
  owner_name: "Nabhila",
  age_range: "0-6",
  years: "3",
  infant_capacity: "15",
  toddler_capacity: "20",
  preschool_capacity: "25",
  contact_phone: "555-1357",
  contact_email: "nabila@example.com",
},

推荐答案

正如我在对你的问题的 comments 中所建议的,你应该只使用一个支持Advanced Markers的不同库.因为Advanced Markers允许您将标记纯作为HTML元素加载.

在这种情况下,我建议您使用@vis.gl/react-google-maps及其相应的<AdvancedMarker>组件.

为了实现它,您应该遵循前面提到的库中关于如何加载map和高级标记的文档.

然后,要将其用于您的数据,您应该在加载标记时使用array.map().它将遍历您的数据,并使用这些数据传递到AdvancedMarker组件渲染中.你的代码应该看起来像这样:

import React from "react";
import { createRoot } from "react-dom/client";

import { AdvancedMarker, APIProvider, Map } from "@vis.gl/react-google-maps";

const API_KEY =
  globalThis.GOOGLE_MAPS_API_KEY ?? (process.env.GOOGLE_MAPS_API_KEY as string);

const App = () => {
  var childCareData = [
    {
      childcare_name: "East Side Preschool",
      address: "458 Fairall Street",
      city: "Ajax",
      region: "Ontario",
      postalcode: " L1S 1R6",
      country: "CANADA",
      latitude: "43.75991",
      longitude: "-79.18827",
      owner_name: "Jessica Lee",
      age_range: "2-6",
      years: "4",
      infant_capacity: "8",
      toddler_capacity: "12",
      preschool_capacity: "18",
      contact_phone: "555-9012",
      contact_email: "jessica@example.com",
    },
    {
      childcare_name: "Kepalen Angelic Child Care Daycare",
      address: "1301 Neilson Rd",
      city: "Scarborough",
      region: "Ontario",
      postalcode: "M1B 3C2",
      country: "Canada",
      latitude: "43.80716",
      longitude: "-79.21856",
      owner_name: "Nabhila",
      age_range: "0-6",
      years: "3",
      infant_capacity: "15",
      toddler_capacity: "20",
      preschool_capacity: "25",
      contact_phone: "555-1357",
      contact_email: "nabila@example.com",
    },
  ];
  return (
    <APIProvider apiKey={API_KEY} libraries={["marker"]}>
      <Map
        mapId={"bf51a910020fa25a"}
        defaultZoom={12}
        defaultCenter={{ lat: 43.77887, lng: -79.17282 }}
        gestureHandling={"greedy"}
        disableDefaultUI
      >
        {childCareData &&
          childCareData.map((childCare, key) => {

            /* Convert your longitude and latitude into a float first
             since your data stored it as a string. */

            const floatLat = parseFloat(childCare.latitude);
            const floatLng = parseFloat(childCare.longitude);
            return (
              <AdvancedMarker
                key={key}
                position={{ lat: floatLat, lng: floatLng }}
                title={"AdvancedMarker with custom html content."}
              >
                <div
                  style={{
                    width: 16,
                    height: 16,
                    position: "absolute",
                    background: "#1dbe80",
                    border: "2px solid #0e6443",
                    borderRadius: "50%",
                    transform: "translate(-50%, -50%)",
                  }}
                >
                  <h3
                    style={{
                      padding: 12,
                    }}
                  >
                    {childCare.childcare_name}
                  </h3>
                </div>
              </AdvancedMarker>
            );
          })}
      </Map>
    </APIProvider>
  );
};

export default App;

export function renderToDom(container: HTMLElement) {
  const root = createRoot(container);

  root.render(
    <React.StrictMode>
      <App />
    </React.StrictMode>,
  );
}

然后,这应该像预期的那样工作,而不会在移动 map 时出现位置问题.

Map with marker sample

这里有一个proof of concept codesandbox,你可以try 和判断自己.

Node.js相关问答推荐

无法在我的 node 项目中转让Google Drive v3 API中的所有权

当建议在第二代上运行云功能时,现在是否有新的Firestore AdminClient可供使用?

findoneandupdate()方法更新数据库,但其响应在请求中返回为null

是否可以在MongoDB中比较和匹配引用文档中的字段

Sass-TypeError:无法读取未定义的属性(正在读取';indexOf';)

Inno Setup如何在现有文本文件中追加新内容

将代码转换为 ES6 Discord.js 的问题

Pug - 包括带有include关键字的c代码

GridFS 大文件下载使 Node.js 服务器崩溃. MongoServerError:排序超出了字节的内存限制

Cypress net::ERR_EMPTY_RESPONSE 在真实服务器调用上

如何使用 mocha.js 模拟用于单元测试的依赖类?

Chrome 浏览器未将 if-modified-since 标头发送到服务器

如何将`yarn.lock`与`package.json`同步?

向 Stripe 提交付款请求时出现没有此类令牌错误

Node.js `--nolazy` 标志是什么意思?

名称类型为 mongoose 的字段

在 Node.js 上使用 Connect 无法获取 /

如何断言不为空?

promise 回调返回promise

node.js 中的意外保留字导入