How to get LatLng of Touch on Leaflet - javascript

I'd like to get the LatLng of the touchpoint in a touchmove event (leaflet map). I didn't find a way to solve this. Are there any ways to get the coordinates?
$(document).on('touchmove', '#mapid', function(e) {
//here i want to get the LatLng coordinates
)};

I see two approaches.
One is to use Leaflet's event handling, y doing something like map.on('mousemove', function(ev){ ... });.
That event handler will receive a Leaflet 'MouseEvent', which includes the LngLat of the point of the map where the event took place. See http://leafletjs.com/reference-1.1.0.html#map-event and http://leafletjs.com/reference-1.1.0.html#mouseevent. And yes, Leaflet listens to TouchEvents and PointerEvents when told to listen to MouseEvents.
The other approach is to use the map's containerPointToLatLng() conversion method, or the mouseEventToLatLng() method to turn a pixel coordinate or a mouse event into a LatLng.

Related

Google Maps API Drawing Manager: remove double-click to close polygon or change sensitivity

When I'm drawing a polygon with Google Maps Api DrawingManager, I use the event listener 'polygoncomplete' to do some actions:
google.maps.event.addListener(drawingManager, 'polygoncomplete', function(poly) {
// Some actions here...
}
Sometimes, especially using the Apple Pencil on iPadPro, the event raises even when not expected: usually it is because I place two vertex one next to the other (but not so much as expected to close polygon).
I wonder if there is a way to control the 'double-click' sensitivity to raise the polygoncomplete event, or if there is a workaround to raise the event in a custom way (ex. clicking a button).
From This question I understand (and tried too) that preventDefault and stopPropagation are not working if used in Maps Api events.
I got the same problem. When you make a double click after the first point, it automatically closes the polygon (with 2 points only). In the callback I make a check, if the points in the polygon are less than 3, do nothing. You can try it with the following code:
google.maps.event.addListener(drawingManager, 'polygoncomplete', function(poly) {
if (poly.getPath().length < 3) {
return;
}
// Some actions here...
}
It's a workaround but works for me. In my case I did that check after showing the poly to the map, so before the 'return' I remove the poly from the map, but that works for me.

Is there an event that is fired when the map is done rendering?

I am looking for an event that is fired on zoomend AND/OR moveend. Basically I have a popup that needs to happen after either of these events, and that popup depends on queryRenderedFeatures, which can only be queried if they are in the map view.
I am currently using a setTimeout function if there is not zoomend, but this is not ideal. Yes, I can attach functions after both of these, but this get messy. I see there is a map.on('data') event, but is there a map.on('data.load') or something similar, like on map.on('style.load')?
What I am wanting is something that is fired after there is no longer any map.on('data') events firing. Maybe this can be done in Javascript with setInterval or something.
Thanks
You can bind your query function to map.on('move', function() {}) which will fire continuously as the map is being zoomed or dragged.
In my application, I use map.on('move', function() {}) to get the center lat/lng of the map. So my code roughly looks like this:
setCenter () {
const center = map.getCenter()
// render the center coords
}
// later in my code
map.on('move', this.setCenter)
// and when I'm done
map.off('move', this.setCenter)

Event viewreset is not fired in leaflet version 1.0.2

I am using d3 with Leaflet (v 1.0.2) and need to catch the viewreset event, but it's not fired.
this.map.on("viewreset", () => console.log("VIEW RESET"));
Is anyone else having this problem? I'm able to catch the zoomend event for example.
Also, manipulating positions and etc. on svg-layers is a bit of a pain as well in the new versions of Leaflet...but that is another story.
JSFidlle showing the problem http://leafletjs.com/reference-1.0.2.html
According to: https://github.com/Leaflet/Leaflet/issues/4837
in 1.0, layers will have to rely on both zoom (zoom change) and viewreset (full reset of a layer). This was necessary to implement flyTo and other arbitrary animations.
And in: https://github.com/Leaflet/Leaflet/pull/3278
remove viewreset event and depend solely on zoom event in layers instead
So viewreset event is no longer triggered on zoom.

How to implement "zoom" and "drag" functionality in Bing Maps 7.0?

I am developing a web application that uses Bing maps 7.0. I was wondering if there was a way to bind a function to a Map class event that listens for when the map is either dragged or zoomed. From what I see in the documentation, the viewchangeend event for the Map class is close to what I am looking for, however this event is called in situations that I do not particularly want to account for, such as if I hide the map's containing div using jQuery or on map creation/initialization. Ideally, I would also like this to be a throttled event, where the handler function gets called after a given amount of time. Any idea on how this could be implemented?
Update
As suggested by psousa, I used the viewchangeend event.
This is the hack around that I tried implementing to sort of try and detect if the map has zoomed or been dragged. I still bind the handler to the viewchangeend event, but this time I check to see if the Northwest coordinates or Southeast coordinates of the map have changed.
var map; // contains Microsoft.Maps.Map instance
var nw; // contains the NW Microsoft.Maps.LocationRect instance
var se; // contains the SE Microsoft.Maps.LocationRect instance
// initialization code goes here some where
Microsoft.Maps.Events.addThrottledHandler(map, "viewchangeend", function(arg) {
var curNW = map.getBounds().getNorthwest();
var curSE = map.getBounds().getSoutheast();
if (nw.latitude != curNW.latitude ||
nw.longitude != curNW.longitude ||
se.latitude != curSE.latitude ||
se.longitude != curSE.longitude)
{
nw = curNW;
se = curSE;
// Execute actual handler code here
}
}, 1000);
This code does not work as I had intended. As I'm debugging the code, if I go and hide the map's containing div (using jQuery), I notice that curNW and and curSE do not have the same coordinates as the ones I stored on the previous call. Why is this if I never dragged the map around or zoomed in or out? I am just hiding the map, why would the map's coordinates change? It makes no sense to me. Ideally, I wish Bing maps would provide developers with a zoomend or dragend event so I can say:
Microsoft.Maps.Map.addThrottledHandler(map, "zoomend", handler, 1000);
Microsoft.Maps.Map.addThrottledHandler(map, "dragend", handler, 1000);
Google Maps I believe provides this functionality. If anyone knows a better way to check for these events, please let me know. I don't want to add additional handlers to the elements of the page that may trigger a viewchangeend as there is way to much stuff going on in this page as it is. Appreciate the help.
The viewchangeend and viewchange are the best events for that, so no great alternative there.
Anyway, you have out-of-the-box support for throttled events. So, instead of:
Microsoft.Maps.Events.addHandler(map, 'viewchangeend', handler);
you can just use (the last argument uses milliseconds):
Microsoft.Maps.Events.addThrottledHandler(map, 'viewchangeend', handler, 500);
Reference: http://msdn.microsoft.com/en-us/library/gg427623.aspx

How to fire action when ANY Google Map Event Has Been Fired

I am implementing an app using Google Maps API 3. I would like to know what is the best implementation in dealing with this problem. I want to execute an action once ANY event in Google Map has been fired. Currently, what I am doing is that I call the function every time a specific event is called. I find this redundant and I have to make a listener for all of the events. So, is there a way to generalize this where I can do the following:
google.maps.addListener(everything_on_the_map_canvas, 'ANY_EVENT', function(event) {
foo();
})
function foo(){
//do something here
}
Thank you.
If the user decides to continue with map operations, they will have to move the mouse over the map to do anything. So you could simply trap a mousemove.
google.maps.event.addListener(map, 'mousemove', function(event) {foo();})
If the user can manipulate the map without moving the mouse over the map, then you will need to listen to other events.
bounds_changed will cover most eventualities with zoom and pan, heading and the like
maptype_id_changed
But that's only three instead of all of them. If the bounds don't change when the tilt does (and you can change tilt from outside the map) you may need to listen for tilt_changed as well.

Categories

Resources