javascript - 鼠标悬停在 div 项目上时如何在地图中显示标记位置 - 例如 AirBnb
问题描述
我在左侧 div 项目中有一个页面,例如项目的图像、标题、详细信息、地址 ex。在右侧,我有一张地图(传单地图),显示了从所有这些左侧项目中获取的地址标记。现在,当鼠标悬停到带有地址的左侧信息时,我想在地图上显示标记位置。很快您就可以在airbnb.com上看到实时示例
如您所见,我正在使用 React Leaflet 作为地图和 React。但是数据还没有从数据库中获取,它是虚拟数据。地址由 lat 和 lng 坐标定义
自行车.js
import { BIKES, BikeTypes, BikeSize } from '../../data'
const Bikes = () => {
return <div className="bikes-page">
<div>
<hr className="bike-bottom-line" />
<BikesList items={BIKES} />
</div>
<div className="bikes-map">
<MapContainer style={{ height: '50rem' }} coords={BIKES} mapZoom={9} />
</div>
</div>
}
export default Bikes
MapContainer.js(使用 react-leaflet 制作的组件)
const MapContainer = (props) => {
const DEFAULT_LATITUDE = 40.500;
const DEFUALT_LANGITUDE = 49.500;
return (
<Map style={props.mapStyle} center={[DEFAULT_LATITUDE, DEFUALT_LANGITUDE]} zoom={props.mapZoom || 7} >
<TileLayer
url="https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png"
attribution='© <a href="http://osm.org/copyright">OpenStreetMap</a> contributors'
/>
{
props.coords ?
props.coords.map(mark => {
return <Marker
position={[mark.location.lat, mark.location.lng]}
icon={biker}
key={mark.id} >
<Popup className="popup">
<Link to={`/b/${mark.id}`} className="popup-container">
<img src={mark.images[0]} alt={mark.title} />
<div className="popup-container__title">
<h3> {mark.title} </h3>
{mark.size}" · {mark.price.first}azn/s
</div>
</Link>
</Popup>
</Marker>
}) : null
}
</Map >
)
}
export default MapContainer
BikesList.js (左侧 - 列表)
const BikesList = (props) => {
if (props.items.length === 0) {
return <h2>Elan tapılmadı</h2>
}
return (
<ul className="bikes-list">
{props.items.map((bike) => (
<BikeItem
key={bike.id}
id={bike.id}
image={bike.images[0]}
title={bike.title}
city={bike.city}
size={bike.size}
price={bike.price.first}
creator={bike.creator}
maxLength={24}
/>
))}
</ul>
)
}
export default BikesList
解决方案
我自己找到了解决方案。这很容易:) 这里是:
首先,在 Bikes.js 文件中,我创建了一个isHovered状态并将其默认设置为 null。然后使用 id 制作 handleHoverMarker(id) 函数,该函数将从特定悬停项目的 id 中获取它。在函数中,我将 setIsHovered 的值更改为这个发送的 id。于是我用道具分享了isHovered和handleHoverMarker。
自行车.js
const [isHovered, setIsHovered] = useState(null)
const handleHoverMarker = (id) => {
setIsHovered(id)
}
<div>
<BikesList handleHoverMarker={handleHoverMarker} items={filteredDataState} />
</div>
<div className="bikes-map">
<MapContainer isHovered={isHovered} style={{ height: '50rem' }} coords={BIKES} mapZoom={9} />
</div>
其次,handleHoverMarker道具发送到 BikeItem 组件,该组件代表列表中的每个项目。
BikesList.js
<ul className="bikes-list">
{props.items.map((bike) => (
<BikeItem
key={bike.id}
id={bike.id}
image={bike.images[0]}
title={bike.title}
city={bike.city}
size={bike.size}
price={bike.price.first}
creator={bike.creator}
maxLength={24}
handleHoverMarker={props.handleHoverMarker}
/>
))}
</ul>
在BikeItem.js 中设置 mouseHover 事件并使用handleHoverMarker(id)函数传递 id。所以我们将知道哪个项目与 id 悬停。
注意:我没有在 BikeItem.js 中编写所有代码,只做了必要的部分
BikeItem.js
<li onMouseEnter={()=> props.handleHoverMarker(props.id):null} onMouseLeave={()=>props.handleHoverMarker(null):null} key={props.id}>
所以在这里我们回到 MapContainer,它将显示悬停项目的位置
MapContainer.js
{props.coords ?
props.coords.map(mark => {
return <Marker
position={[mark.location.lat, mark.location.lng]}
icon={biker}
opacity={props.isHovered === mark.id ? .7 :1}
key={mark.id} >
<Popup className="popup">
<Link to={`/b/${mark.id}`} className="popup container">
<div className="popup-container__title">
<h3> {mark.title}</h3>
</div>
</Link>
</Popup>
</Marker>
}) : null}
在这里,我使用从 Bikes.js 文件发送的 props.isHovered 有条件地更改了不透明度值。
注意:我无法更改标记的样式,因为我没有从传单地图的文档中找到方法。所以逻辑是一样的,你也可以用谷歌地图来做。祝你好运:)
推荐阅读
- google-apps-script - 在 Apps 脚本中获取 sheet.getRange 中生成的超链接
- firebase - 在前端调用它时等待 httpsCallable 似乎不起作用
- sql-server - 赛普拉斯在连接到端口 4400 上的网络 SQL Server 时附加端口 1433
- github - GitHub - 启用“评论”事件/错误:无法处理 webhook
- android - 如何每 24 小时更新一次 Android SQLite 数据库?
- hive - 将 Hive MultiSerde 中的记录插入 Hive 中的 Parquet 表
- excel - 双击工作表中的单元格以在另一个工作表中生成过滤数据
- python - 如何在 python-docx 中突出显示标题
- ruby-on-rails - dry-rails 如何使用合同验证
- python - 如何在python中计算椭圆和直线的交点?