I have a leaflet map up and running. It overlays a series of polygons (via GeoJSON) on the map and attaches popups to each polygon. Each of the popups display information about that polygon.
我有一张宣传单,上面有张地图。它在地图上覆盖了一系列多边形(通过GeoJSON),并将弹出窗口连接到每个多边形上。每个popups都显示关于这个多边形的信息。
I'd like to have inside the popup a link that, when clicked, runs a javascript function that pulls further smaller polygons via AJAX and shows them.
我希望在弹出的链接中有一个链接,当点击它时,它会运行一个javascript函数,通过AJAX将更小的多边形拉出来并显示出来。
I can't get the script to catch a click on the link via the normal jQuery/Javascript click events. Here's what I mean by normal (the following doesn't work):
我无法让脚本通过正常的jQuery/Javascript点击事件来捕捉链接。以下是我所说的正常(以下不适用):
$('a .smallPolygonLink').click(function(e){
console.log("One of the many Small Polygon Links was clicked");
});
The bindPopup part is as follows. It runs on each polygon when made and it pops up correctly on clicking on a polygon. It does show the link, just won't run the above code on click.
bindPopup部分如下。当它在每个多边形上运行时,它会在一个多边形上正确弹出。它确实显示了链接,只是不会在click上运行上面的代码。
var popupContent = "Basic Information..." + '<a class="smallPolygonLink" href="#">Click here to see the smaller polygons</a>';
layer.bindPopup(popupContent);
Here's a JSFiddle illustrating the example, though in a far simpler form. http://jsfiddle.net/2XfVc/4/
这是一个以简单得多的形式说明例子的JSFiddle。http://jsfiddle.net/2XfVc/4/
7 个解决方案
#1
42
The link element inside the popup is being dynamically generated from your markup each time the popup is opened. That means the link doesn't exist when you're trying to bind the handler to it.
弹出窗口中的链接元素是在每次打开弹出窗口时动态生成的。这意味着当您试图将处理程序绑定到它时,链接并不存在。
The ideal approach here would be to use on
to delegate event handling to the popup element or an ancestor of it. Unfortunately, the popup prevents event propagation, which is why delegating event handling to any static elements outside the popup won't work.
这里的理想方法是将事件处理委托给popup元素或它的祖先。不幸的是,弹出窗口阻止事件传播,这就是为什么将事件处理委托给弹出窗口之外的任何静态元素都不起作用。
What you can do is preconstruct the link, attach the handler, and then pass it to the bindPopup
method.
您可以做的是预先构建链接,附加处理程序,然后将其传递给bindPopup方法。
var link = $('<a href="#" class="speciallink">TestLink</a>').click(function() {
alert("test");
})[0];
marker.bindPopup(link);
Here is a demonstration: http://jsfiddle.net/2XfVc/7/
这里有一个演示:http://jsfiddle.net/2XfVc/7/。
In general, to insert any sort of complex markup with multiple event handlers, use the folowing approach:
一般来说,要在多个事件处理程序中插入任何类型的复杂标记,使用folowing方法:
// Create an element to hold all your text and markup
var container = $('<div />');
// Delegate all event handling for the container itself and its contents to the container
container.on('click', '.smallPolygonLink', function() {
...
});
// Insert whatever you want into the container, using whichever approach you prefer
container.html("This is a link: <a href='#' class='smallPolygonLink'>Click me</a>.");
container.append($('<span class="bold">').text(" :)"))
// Insert the container into the popup
marker.bindPopup(container[0]);
Here is a demo: http://jsfiddle.net/8Lnt4/
这里有一个演示:http://jsfiddle.net/8Lnt4/。
See this Git issue for more on event propagation in leaflet popups.
请参阅此Git问题,以了解更多关于在传单弹出的事件传播的问题。
#2
21
While the Popup content wrapper prevents event propagation, events within the popup inner Markup propagate just fine. You can add events to popup elements when they are displayed on the map (and have become part of the DOM). Just watch for leaflet event popupopen
.
当弹出的内容包装器阻止事件传播时,弹出内部标记中的事件就会传播得很好。您可以将事件添加到显示在地图上的弹出元素(并已成为DOM的一部分)。只需要注意单张事件弹出窗口。
var map = L.map('map').setView([51.505, 10], 7); //for example
//the .on() here is part of leaflet
map.on('popupopen', function() {
$('a .smallPolygonLink').click(function(e){
console.log("One of the many Small Polygon Links was clicked");
});
});
http://jsfiddle.net/tJGQ7/2/
This works like a charm for me. If your popup does not have a 'a .smallPolygonLink'
the above code does nothing. This code runs on every startup of a popup. However you don't have to worry that it attaches more than one handler to an element, since when the popup closes, the DOM nodes get thrown away.
这对我来说是一种魅力。如果你的弹出窗口没有“a . smallpolygonlink”,上面的代码什么也不做。这段代码在弹出的每个启动程序上运行。但是,您不必担心它将多个处理程序连接到一个元素,因为当弹出窗口关闭时,DOM节点会被丢弃。
There is a much more general way to do this. However, it involves eval()
. Use at your own risk. But when AJAXloading partial pages that contain JS you run the same risks, so for your edification I present "executing JS inside your leaflet popups":
有一个更普遍的方法。然而,它涉及eval()。使用自己的风险。但是,当AJAXloading部分页面包含JS时,您也会运行相同的风险,因此,对于您的编辑,我现在将“在您的页面弹出窗口中执行JS”:
map.on('popupopen', function(){
var cont = document.getElementsByClassName('leaflet-popup-content')[0];
var lst = cont.getElementsByTagName('script');
for (var i=0; i<lst.length;i++) {
eval(lst[i].innerText)
}
});
demo: http://jsfiddle.net/tJGQ7/4/
演示:http://jsfiddle.net/tJGQ7/4/
Now you can write:
现在您可以编写:
var popup_content = 'Testing the Link: <a href="#" class="speciallink">TestLink</a><script> $(".speciallink").on("click", function(){alert("hello from inside the popup")});</script>';
marker.bindPopup(popup_content);
#3
4
That's what I find on the mapbox offical website: Create a click event in a marker popup with Mapbox.js and jQuery. The comment explains why we say $('#map')
instead of $('#mybutton')
.
这就是我在mapbox offical网站上找到的:在一个带有mapbox的标记中创建一个点击事件。js和jQuery。注释解释了为什么我们说$('#map')而不是$('#mybutton')。
var marker = L.marker([43.6475, -79.3838], {
icon: L.mapbox.marker.icon({
'marker-color': '#9c89cc'
})
})
.bindPopup('<button class="trigger">Say hi</button>')
.addTo(map);
//The HTML we put in bindPopup doesn't exist yet, so we can't just say
//$('#mybutton'). Instead, we listen for click events on the map element which will bubble up from the tooltip, once it's created and someone clicks on it.
$('#map').on('click', '.trigger', function() {
alert('Hello from Toronto!');});
#4
3
I came across this problem, tried the solution above. But it didn't worked for me. Found the following pretty basic jquery solution.
我遇到了这个问题,尝试了上面的解决方案。但它对我不起作用。找到了以下基本的jquery解决方案。
// add your marker to the map
var my_marker = new L.marker([51.2323, 4.1231], {icon: my_icon});
var popup = L.popup().setContent('<a class="click" href="#">click</a>');
my_marker.addTo(map).bindPopup(popup);
// later on
jQuery("body").on('click','a.click', function(e){
e.preventDefault();
alert('clicked');
});
#5
1
You can use jQuery to select the canvas
element, but you'd have to use its own methods within the canvas. A decent start would be https://developer.mozilla.org/en/canvas_tutorial .
您可以使用jQuery选择画布元素,但是您必须在画布中使用它自己的方法。一个好的开始将是https://developer.mozilla.org/en/canvas_tutorial。
#6
0
You can check inner properties of popup
object, including _wrapper
etc.
您可以检查弹出对象的内部属性,包括_wrapper等。
map.on('popupopen', _bindPopupClick);
map.on('popupclose', _unbindPopupClick);
var _bindPopupClick = function (e) {
if (e.popup) {
e.popup._wrapper.addEventListener('click', _bindPopupClickHandler);
}
};
var _unbindPopupClick = function (e) {
if (e.popup) {
e.popup._wrapper.removeEventListener('click', _bindPopupClickHandler);
}
}`
#7
0
mapbox JavaScript library has an event:
mapbox JavaScript库有一个事件:
bindPopup('<button class="trigger">Say hi</button>');
addTo(map);
$('#map').on('click', '.trigger', function() {
alert('Hello from Toronto!');
});
https://www.mapbox.com/mapbox.js/example/v1.0.0/clicks-in-popups/
https://www.mapbox.com/mapbox.js/example/v1.0.0/clicks-in-popups/
#1
42
The link element inside the popup is being dynamically generated from your markup each time the popup is opened. That means the link doesn't exist when you're trying to bind the handler to it.
弹出窗口中的链接元素是在每次打开弹出窗口时动态生成的。这意味着当您试图将处理程序绑定到它时,链接并不存在。
The ideal approach here would be to use on
to delegate event handling to the popup element or an ancestor of it. Unfortunately, the popup prevents event propagation, which is why delegating event handling to any static elements outside the popup won't work.
这里的理想方法是将事件处理委托给popup元素或它的祖先。不幸的是,弹出窗口阻止事件传播,这就是为什么将事件处理委托给弹出窗口之外的任何静态元素都不起作用。
What you can do is preconstruct the link, attach the handler, and then pass it to the bindPopup
method.
您可以做的是预先构建链接,附加处理程序,然后将其传递给bindPopup方法。
var link = $('<a href="#" class="speciallink">TestLink</a>').click(function() {
alert("test");
})[0];
marker.bindPopup(link);
Here is a demonstration: http://jsfiddle.net/2XfVc/7/
这里有一个演示:http://jsfiddle.net/2XfVc/7/。
In general, to insert any sort of complex markup with multiple event handlers, use the folowing approach:
一般来说,要在多个事件处理程序中插入任何类型的复杂标记,使用folowing方法:
// Create an element to hold all your text and markup
var container = $('<div />');
// Delegate all event handling for the container itself and its contents to the container
container.on('click', '.smallPolygonLink', function() {
...
});
// Insert whatever you want into the container, using whichever approach you prefer
container.html("This is a link: <a href='#' class='smallPolygonLink'>Click me</a>.");
container.append($('<span class="bold">').text(" :)"))
// Insert the container into the popup
marker.bindPopup(container[0]);
Here is a demo: http://jsfiddle.net/8Lnt4/
这里有一个演示:http://jsfiddle.net/8Lnt4/。
See this Git issue for more on event propagation in leaflet popups.
请参阅此Git问题,以了解更多关于在传单弹出的事件传播的问题。
#2
21
While the Popup content wrapper prevents event propagation, events within the popup inner Markup propagate just fine. You can add events to popup elements when they are displayed on the map (and have become part of the DOM). Just watch for leaflet event popupopen
.
当弹出的内容包装器阻止事件传播时,弹出内部标记中的事件就会传播得很好。您可以将事件添加到显示在地图上的弹出元素(并已成为DOM的一部分)。只需要注意单张事件弹出窗口。
var map = L.map('map').setView([51.505, 10], 7); //for example
//the .on() here is part of leaflet
map.on('popupopen', function() {
$('a .smallPolygonLink').click(function(e){
console.log("One of the many Small Polygon Links was clicked");
});
});
http://jsfiddle.net/tJGQ7/2/
This works like a charm for me. If your popup does not have a 'a .smallPolygonLink'
the above code does nothing. This code runs on every startup of a popup. However you don't have to worry that it attaches more than one handler to an element, since when the popup closes, the DOM nodes get thrown away.
这对我来说是一种魅力。如果你的弹出窗口没有“a . smallpolygonlink”,上面的代码什么也不做。这段代码在弹出的每个启动程序上运行。但是,您不必担心它将多个处理程序连接到一个元素,因为当弹出窗口关闭时,DOM节点会被丢弃。
There is a much more general way to do this. However, it involves eval()
. Use at your own risk. But when AJAXloading partial pages that contain JS you run the same risks, so for your edification I present "executing JS inside your leaflet popups":
有一个更普遍的方法。然而,它涉及eval()。使用自己的风险。但是,当AJAXloading部分页面包含JS时,您也会运行相同的风险,因此,对于您的编辑,我现在将“在您的页面弹出窗口中执行JS”:
map.on('popupopen', function(){
var cont = document.getElementsByClassName('leaflet-popup-content')[0];
var lst = cont.getElementsByTagName('script');
for (var i=0; i<lst.length;i++) {
eval(lst[i].innerText)
}
});
demo: http://jsfiddle.net/tJGQ7/4/
演示:http://jsfiddle.net/tJGQ7/4/
Now you can write:
现在您可以编写:
var popup_content = 'Testing the Link: <a href="#" class="speciallink">TestLink</a><script> $(".speciallink").on("click", function(){alert("hello from inside the popup")});</script>';
marker.bindPopup(popup_content);
#3
4
That's what I find on the mapbox offical website: Create a click event in a marker popup with Mapbox.js and jQuery. The comment explains why we say $('#map')
instead of $('#mybutton')
.
这就是我在mapbox offical网站上找到的:在一个带有mapbox的标记中创建一个点击事件。js和jQuery。注释解释了为什么我们说$('#map')而不是$('#mybutton')。
var marker = L.marker([43.6475, -79.3838], {
icon: L.mapbox.marker.icon({
'marker-color': '#9c89cc'
})
})
.bindPopup('<button class="trigger">Say hi</button>')
.addTo(map);
//The HTML we put in bindPopup doesn't exist yet, so we can't just say
//$('#mybutton'). Instead, we listen for click events on the map element which will bubble up from the tooltip, once it's created and someone clicks on it.
$('#map').on('click', '.trigger', function() {
alert('Hello from Toronto!');});
#4
3
I came across this problem, tried the solution above. But it didn't worked for me. Found the following pretty basic jquery solution.
我遇到了这个问题,尝试了上面的解决方案。但它对我不起作用。找到了以下基本的jquery解决方案。
// add your marker to the map
var my_marker = new L.marker([51.2323, 4.1231], {icon: my_icon});
var popup = L.popup().setContent('<a class="click" href="#">click</a>');
my_marker.addTo(map).bindPopup(popup);
// later on
jQuery("body").on('click','a.click', function(e){
e.preventDefault();
alert('clicked');
});
#5
1
You can use jQuery to select the canvas
element, but you'd have to use its own methods within the canvas. A decent start would be https://developer.mozilla.org/en/canvas_tutorial .
您可以使用jQuery选择画布元素,但是您必须在画布中使用它自己的方法。一个好的开始将是https://developer.mozilla.org/en/canvas_tutorial。
#6
0
You can check inner properties of popup
object, including _wrapper
etc.
您可以检查弹出对象的内部属性,包括_wrapper等。
map.on('popupopen', _bindPopupClick);
map.on('popupclose', _unbindPopupClick);
var _bindPopupClick = function (e) {
if (e.popup) {
e.popup._wrapper.addEventListener('click', _bindPopupClickHandler);
}
};
var _unbindPopupClick = function (e) {
if (e.popup) {
e.popup._wrapper.removeEventListener('click', _bindPopupClickHandler);
}
}`
#7
0
mapbox JavaScript library has an event:
mapbox JavaScript库有一个事件:
bindPopup('<button class="trigger">Say hi</button>');
addTo(map);
$('#map').on('click', '.trigger', function() {
alert('Hello from Toronto!');
});
https://www.mapbox.com/mapbox.js/example/v1.0.0/clicks-in-popups/
https://www.mapbox.com/mapbox.js/example/v1.0.0/clicks-in-popups/