gpt4 book ai didi

javascript - Mapbox.js - 单击列表中的项目并平移到标记并显示弹出窗口

转载 作者:行者123 更新时间:2023-12-03 09:56:37 26 4
gpt4 key购买 nike

我从一个 .js 文件开始,并对其进行了修改,以便它:1. 过滤geoJSON中的数据(右上角按钮)
2. 单击标记时显示包含相关数据的弹出窗口
3. 根据入站标记或 map 上当前显示的标记显示商店列表。放大时,左侧列出的标记和项目也会减少。

现在我无法让这两个工作:

  1. 带有“item”的 Div 类发生更改,以便将“active”添加到类名
  2. 当我单击左侧列表中的链接时,列表项不会平移到单击的标记并不再显示弹出窗口。相反,它一次显示列表中所有位置的标记,以最后一个结束。我确信它与locations.eachLayer 有关,但我不知道如何修复它,以便它显示数据或选择我想要的数据。我有一种感觉,我可能也没有按照正确的顺序使用事件处理程序。

视觉
OLD FILE: When I click on an item in the list on the left, the map automatically pans to and opens up that marker and popup.
NEW FILE (in progress): Trying to get it to work

// *****This is the map
L.mapbox.accessToken = 'pk.eyJ1IjoiamVubmlmZXJwaGFtIiwiYSI6Ijc3NmJkZWE1YjM0ZDc0MWU2Yzc0MWM0YWQ5NzRiNzliIn0.OaKjiklBTRs_Saoh1wSglw';
var map = L.mapbox.map('map', 'glidewell.jno36i2l');
// END of the map

$( document ).ready(function() {


// ******This code zooms to the country locations listed on the page
document.getElementById('navigation').onclick = function(e) {
e.preventDefault();
var pos = e.target.getAttribute('data-position');
var zoom = e.target.getAttribute('data-zoom');
if (pos && zoom) {
var loc = pos.split(',');
var zoo = parseInt(zoom);
map.setView(loc, zoo);
return false;
}
}
// END of that code


//this calls the <div id="listings>
var listings = document.getElementById('listings');
// *****This brings in the locations or GEO JSON file
var locations = L.mapbox.featureLayer().addTo(map);
var listing = $('div.item');
var link = $('a.title');

//this is the file that the data comes from
locations.loadURL('js/testingdummydata.geojson');
// END of that code

// ****** This code zooms to the point on hr map when a selection is made from the list
function setActive(el) {
var siblings = listings.getElementsByTagName('div');
for (var i = 0; i < siblings.length; i++) {
siblings[i].className = siblings[i].className
.replace(/active/, '').replace(/\s\s*$/, '');
}

el.className += ' active';
}
// END of that code


// *****This code merges the Map and the list together
locations.on('ready', makepopup).on('ready', showMarkersinBound)
.on('ready', goToMarker);


function makepopup() {
locations.eachLayer(function (locale) {

var prop = locale.feature.properties;
// Shorten locale.feature.properties to just `prop` so we're not
// writing this long form over and over again.
var popup = '<h3>' + prop.title + '</h3><div>' + prop.address + '<br>' + prop.city + ', ' + prop.state + '<br>' + prop.phone + '<br>' + '<a href="http://' + prop.website + '" target="_blank">' + prop.website + '</a>';

if (prop.crossStreet) {
// link.innerHTML += '<br /><small class="quiet">' + prop.crossStreet + '</small>';
popup += '<br /><small class="quiet">' + prop.crossStreet + '</small>';
};



// Marker interaction
locale.on('click', function (e) {
// 1. center the map on the selected marker.
map.panTo(locale.getLatLng());

// 2. Set active the markers associated listing.
setActive(listing);
});

popup += '</div>';
locale.bindPopup(popup);
});
};

function goToMarker(){

locations.eachLayer(function (locale) {

$("a[href='#'][class='title']").click(function () {
setActive(listing);
// When a menu item is clicked, animate the map to center
// its associated locale and open its popup.
map.setView(locale.getLatLng(), 16);

locale.openPopup();
return false;
});
});
};


// *****Filters

$('.menu-ui-btn a').on('click', function() {
//adds "active" class to the link being clicked on and removes active class from the other links in menu
$(this).addClass('active').siblings().removeClass('active');
// For each filter link, get the 'data-filter' attribute value and assign it to a variable called filter.
var filter = $(this).data('filter');
// The setFilter function takes a GeoJSON feature object
// and returns true to show it or false to hide it.
locations.setFilter(function(feature) {
return (filter === 'all') ? true : feature.properties[filter] === true;
});
makepopup();
showMarkersinBound();
return false;
});

//*******LIST OF MARKERS INSIDE VIEW

function showMarkersinBound() {
// Construct an empty list to fill with onscreen markers.
var inBounds = [];

// Get the map bounds - the top-left and bottom-right locations.
var bounds = map.getBounds();

// For each marker, consider whether it is currently visible by comparing
// with the current map bounds.
locations.eachLayer(function (marker, locale) {
if (bounds.contains(marker.getLatLng())) {
var oneListing;
var prop = marker.toGeoJSON().properties;

oneListing= '<div class="item"><a href="#" class="title">' + prop.title + '</a>' + prop.city;
if (prop.state) {
oneListing += ', ' + prop.state;
};
oneListing += '</div>';
inBounds.push(oneListing); //adds the oneListing item into inBounds array
} //closes if statement
});

// Display a list of markers in id="listings" on the DOM.
listings.innerHTML = inBounds.join('');

};


//when map moves, trigger showMarkersinBound function
map.on('move', showMarkersinBound);

});
/* google.com/fonts import files go above this line ^


/* Nav / Menus
================= */
.menu-ui-btn {
background:#fff;
position:absolute;
top:10px;right:10px;
z-index:1;
border-radius:3px;
width:120px;
border:1px solid rgba(0,0,0,0.4);
}
.menu-ui-btn a {
font-size:13px;
color:#404040;
display:block;
margin:0;padding:0;
padding:10px;
text-decoration:none;
border-bottom:1px solid rgba(0,0,0,0.25);
text-align:center;
}
.menu-ui-btn a:first-child {
border-radius:3px 3px 0 0;
}
.menu-ui-btn a:last-child {
border:none;
border-radius:0 0 3px 3px;
}
.menu-ui-btn a:hover {
background:#f8f8f8;
color:#404040;
}
.menu-ui-btn a.active,
.menu-ui-btn a.active:hover {
background:#3887BE;
color:#FFF;
}


/* Content
================= */

#marker-list {
position:absolute;
top:0; right:0;
width:200px;
bottom:0;
overflow-x:auto;
background:#fff;
margin:0;
padding:5px;
height: 400px;
z-index: 50;
background-color: white;
}
#marker-list li {
padding:5px;
margin:0;
list-style-type:none;
}
#marker-list li:hover {
background:#eee;
}


.sidebar {
position:absolute;
width:25%;
height:100%;
top:0;left:0;
overflow:hidden;
border-right:1px solid rgba(0,0,0,0.25);
}
.pad2 {
padding:20px;
}
.quiet {
color:#888;
}
.map {
position:absolute;
left:25%;
width:75%;
top:0;bottom:0;
}
.heading {
background:#fff;
border-bottom:1px solid #eee;
padding:0 10px;
}
.listings {
height:100%;
overflow:auto;
padding-bottom:60px;
}
.listings .item {
display:block;
border-bottom:1px solid #eee;
padding:10px;
text-decoration:none;
}
.listings .item:last-child { border-bottom:none; }
.listings .item .title {
display:block;
color:#BA222B;
font-weight:700;
}
.listings .item .title small { font-weight:400; }
.listings .item.active .title,
.listings .item .title:hover { color:#bbb; }
.listings .item.active {
background-color:#f8f8f8;
}

::-webkit-scrollbar {
width:22px;
height:3px;
border-left:0;
background:rgba(0,0,0,0.1);
}
::-webkit-scrollbar-track {
background:none;
}
::-webkit-scrollbar-thumb {
background:#BA222B;
border-radius:0;
height: 60px;
}

.clearfix { display:block; }
.clearfix:after {
content:'.';
display:block;
height:0;
clear:both;
visibility:hidden;
}

/* Marker tweaks
====================*/
.leaflet-popup-close-button {
display:none;
}
.leaflet-popup-content {
font:400 15px/22px 'Source Sans Pro', 'Helvetica Neue', Sans-serif;
padding:0;
width: auto;
}
.leaflet-popup-content-wrapper {
padding:0;
}
.leaflet-popup-content h3 {
background:#BA222B;
color:#fff;
margin:0;
display:block;
border-radius:3px 3px 0 0;
font-weight:700;
margin-top:-15px;
}
.leaflet-popup-content div {
padding:10px;
}
.leaflet-container .leaflet-marker-icon {
cursor:pointer;
}
/**********************************************************
Media Querys (480px, 768px, 990px, 1200px, 1500px, 2000px)
***********************************************************/

/* Smaller than
================= */

/* Applied to resolutions less than 2000 (3x) */
@media (max-width: 2000px) {

}

/* Applied to resolutions less than 1740 (2x) */
@media (max-width: 1740px) {

}

/* Applied to resolutions less than 1500 (Xl) */
@media (max-width: 1500px) {

}

/* Applied to resolutions less than 1200 (lg) */
@media (max-width: 1200px) {

}

/* Applied to resolutions less than 990 (md) */
@media (max-width: 990px) {

}

/* Applied to resolutions less than 768 (sm) */
@media (max-width: 768px) {

}

/* Applied to resolutions less than 568 (sm) */
@media only screen and (max-width: 568px) {
.sidebar {
position: absolute;
width: 100%;
height: 60%;
bottom: 0;
left: 0;
overflow: hidden;
border-right: 1px solid rgba(0,0,0,0.25);
top: inherit;
}
.map {
position: absolute;
bottom: 60%;
width: 100%;
top: 0;
left: 0;
}
.heading {
background: #fff;
border-bottom: 1px solid #eee;
height: 60px;
padding: 3px 10px;
}
.leaflet-container .leaflet-control-attribution {
display: none;
}
.listings {
height: 233px;
}
}

/* Applied to resolutions less than 480 (XS) */
@media (max-width: 480px) {

}

/* Larger than
================= */

/* Applied to resolutions larger than 2000 (3x) */
@media (min-width: 2001px) {

}

/* Applied to resolutions larger than 1500 (2x) */
@media (min-width: 1501px) {

}

/* Applied to resolutions larger than 1200 (xl) */
@media (min-width: 1201px) {

}

/* Applied to resolutions larger than 990 (lg) */
@media (min-width: 991px) {

}

/* Applied to resolutions larger than 768 (sm) */
@media (min-width: 769px) {

}

/* Applied to resolutions larger than 480 (xs) */
@media (min-width: 481px) {

}

/***************************************
Default Style Sheet created as part of - The Maui Toolbox
For more information visit: www.mauitoolbox.com
pub-20150501
***************************************/

#coordinates {
height:450px;
overflow:auto;
padding-bottom:60px;
}
#coordinates .item {
display:block;
border-bottom:1px solid #eee;
padding:10px;
text-decoration:none;
}
#coordinates .item:last-child { border-bottom:none; }
#coordinates .item .title {
display:block;
color:#BA222B;
font-weight:700;
}
#coordinates .item .title small { font-weight:400; }
#coordinates .item.active .title,
#coordinates .item .title:hover { color:#bbb; }
#coordinates .item.active {
background-color:#f8f8f8;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta name="Description" content="#"> <!-- (Example: Compelling description to be displayed on Search Engine) -->
<meta name="author" content="#"> <!-- (example: Developers Name) -->
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>[PAGE TITLE]</title>
<!-- (Extrenal) Default Style Sheets =========== -->
<link rel="stylesheet" type="text/css" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.2.0/css/font-awesome.min.css">
<link rel="stylesheet" type="text/css" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.1/css/bootstrap.min.css">
<link rel="stylesheet" type="text/css" href="http://gl-dev-staticweb.s3.amazonaws.com/blimp.css">
<link rel="stylesheet" type="text/css" href="http://gl-dev-staticweb.s3.amazonaws.com/maui.css">
<!-- Style Sheets ============================== -->
<link rel="stylesheet" type="text/css" href="css/map-styles.css">
<!-- Additional Style Sheets =================== -->
<link href='https://fonts.googleapis.com/css?family=Source+Sans+Pro:400,700' rel='stylesheet'>
<script src='https://api.tiles.mapbox.com/mapbox.js/v2.1.9/mapbox.js'></script>
<link href='https://api.tiles.mapbox.com/mapbox.js/v2.1.9/mapbox.css' rel='stylesheet' />

</head>
<body>

<div class='sidebar'>
<div class='heading'>
<h1>ABC Company</h1>
<div class="dropdown">
<a id="dLabel" data-target="#" href="http://example.com" data-toggle="dropdown" aria-haspopup="true" role="button" aria-expanded="false">
Select Country
<span class="caret"></span>
</a>
<ul class="dropdown-menu" role="menu" aria-labelledby="dLabel" id='navigation'>
<li><a href='#' data-zoom="5" data-position='37.0,-95.7'>USA</a></li>
<li><a href='#' data-zoom="8" data-position='56.1,9.5'>DNK</a></li>
<li><a href='#' data-zoom="8" data-position='55.3,-3.4'>GB</a></li>
<li><a href='#' data-zoom="6" data-position='46.2,2.2'>FRA</a></li>
<li><a href='#' data-zoom="7" data-position='41.8,12.5'>ITA</a></li>
<li><a href='#' data-zoom="6" data-position='-30.5,22.9'>ZAF</a></li>
<li><a href='#' data-zoom="6" data-position='20.5,78.9'>IN</a></li>
<li><a href='#' data-zoom="8" data-position='39.0,21.8'>GRC</a></li>
<li><a href='#' data-zoom="6" data-position='26.8,30.8'>EGY</a></li>
<li><a href='#' data-zoom="8" data-position='60.4,8.4'>NOR</a></li>
<li><a href='#' data-zoom="8" data-position='48.6,19.6'>SVK</a></li>
<li><a href='#' data-zoom="5" data-position='-25.3,133.7'>AUS</a></li>
<li><a href='#' data-zoom="8" data-position='-40.9,174.8'>NZ</a></li>
<li><a href='#' data-zoom="5" data-position='35.4,104.1'>CHN</a></li>
<li><a href='#' data-zoom="8" data-position='15.8,100.9'>THA</a></li>
<li><a href='#' data-zoom="8" data-position='52.1,5.2'>NLD</a></li>
<li><a href='#' data-zoom="8" data-position='9.7,-83.7'>CR</a></li>
<li><a href='#' data-zoom="6" data-position='23.6,-102.5'>MX</a></li>
</ul>
</div>
</div>
<div id='listings' class='listings'></div>
</div>

<!-- Filter buttons - filters markers on map-->
<nav class='menu-ui-btn'>
<a href='#' class='active' data-filter='all' id="allfilter">Show all</a>
<a href='#' data-filter='mill' id="millfilter">Mills</a>
<a href='#' data-filter='lab' id="labfilter">Labs</a>
</nav>
<!-- Map is displayed here -->
<div id='map' class='map'></div>

<script src="https://code.jquery.com/jquery-2.1.1.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.2.0/js/bootstrap.min.js"></script>

Mapbox 文档中的 2 个相关示例:
1. 列出标记并平移到单击的项目
2. 列出 View 中的标记

我花了整整 2 天的时间一遍又一遍地研究这个问题,我确实需要有人提供专业的 Javascript 知识,甚至可能是 mapbox.js 经验的帮助。

最佳答案

没关系,我让它工作:

我将 data-name 属性添加到 DOM 中显示的 html 中,以便我可以获得列表中项目的唯一名称(将其添加到“oneListing”变量中)。

function showMarkersinBound() {
// Construct an empty list to fill with onscreen markers.
var inBounds = [];

// Get the map bounds - the top-left and bottom-right locations.
var bounds = map.getBounds();

// For each marker, consider whether it is currently visible by comparing
// with the current map bounds.
locations.eachLayer(function (marker) {
if (bounds.contains(marker.getLatLng())) {
var oneListing;
var prop = marker.toGeoJSON().properties;
//oneListing= '<div class="item"><a href="#" class="title">' + prop.title + '</a><br>' + prop.address + '<br>' + prop.city + ', ' + prop.state + '<br>' + prop.phone + '<br>' + '<a href="http://' + prop.website + '" target="_blank">' + prop.website + '</a></div>';
oneListing= '<div class="item"><a href="#" class="title" data-name="' + prop.title + '">' + prop.title + '</a>' + prop.city;
if (prop.state) {
oneListing += ', ' + prop.state;
};
oneListing += '</div>';
inBounds.push(oneListing); //adds the oneListing item into inBounds array
} //closes if statement
});

// Display a list of markers in id="listings" on the DOM.
listings.innerHTML = inBounds.join('');
}; //closes function

然后函数会遍历所有图层,并且我做了一个 if else 语句,以便仅在单击的链接名称与该图层的标题相同时才更改 View 并平移到标记。

function goToMarker() {

locations.eachLayer(function (layer) {
var itsTitle = layer.toGeoJSON().properties.title;

// var prop = locale.feature.properties;
$(".title").click(function () {
if (($(this).data('name')) === itsTitle) {
// When a menu item is clicked, animate the map to center
// its associated locale and open its popup.
map.setView(layer.getLatLng(), 16);
layer.openPopup();
return false;
};
});
});
}

然后,当位置准备就绪时,我将它们添加为事件监听器。

var locations = L.mapbox.featureLayer().addTo(map);
locations.loadURL('js/testingdummydata.geojson');
locations.on('ready', makepopup).on('ready', howMarkersinBound).on('ready', goToMarker);
//when map moves, trigger showMarkersinBound function
map.on('move', showMarkersinBound).on('move', goToMarker);

关于javascript - Mapbox.js - 单击列表中的项目并平移到标记并显示弹出窗口,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30720776/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com