question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

binding to "touchstart" events on map?

See original GitHub issue

I try to make this work on iOS / Safari:

var map = L.map('map').setView([51.505, -0.09], 13);
map.on('touchstart', function() {
  // does not get here when touching the map
  alert('touchstart')
})

But couldn’t figure out how. It’s not listed in the API reference but I wonder if there is any way to support this event?

Or maybe there is even a better way to achieve the following: I want to add a marker to a map, by touch and holding for a second. It was easy to set this up for mouse events, but I can’t find a way to make the same for touch events.

Any idea?

Issue Analytics

  • State:closed
  • Created 11 years ago
  • Comments:7 (3 by maintainers)

github_iconTop GitHub Comments

7reactions
gr2mcommented, Mar 21, 2013

I found a workaround on the mailing list: https://groups.google.com/forum/?fromgroups=#!topic/leaflet-js/M-6fIg7K1CU

Here it is, slightly adjusted, so it adds support for both, touchstard & touchend:

L.Map.mergeOptions({
  touchExtend: true
});

L.Map.TouchExtend = L.Handler.extend({

  initialize: function (map) {
    this._map = map;
    this._container = map._container;
    this._pane = map._panes.overlayPane;
  },

  addHooks: function () {
    L.DomEvent.on(this._container, 'touchstart', this._onTouchStart, this);
    L.DomEvent.on(this._container, 'touchend', this._onTouchEnd, this);
  },

  removeHooks: function () {
    L.DomEvent.off(this._container, 'touchstart', this._onTouchStart);
    L.DomEvent.off(this._container, 'touchend', this._onTouchEnd);
  },

  _onTouchStart: function (e) {
    if (!this._map._loaded) { return; }

    var type = 'touchstart';

    var containerPoint = this._map.mouseEventToContainerPoint(e),
        layerPoint = this._map.containerPointToLayerPoint(containerPoint),
        latlng = this._map.layerPointToLatLng(layerPoint);

    this._map.fire(type, {
      latlng: latlng,
      layerPoint: layerPoint,
      containerPoint: containerPoint,
      originalEvent: e
    });
  },

  _onTouchEnd: function (e) {
    if (!this._map._loaded) { return; }

    var type = 'touchend';

    this._map.fire(type, {
      originalEvent: e
    });
  }
});
L.Map.addInitHook('addHandler', 'touchExtend', L.Map.TouchExtend);

But maybe there is a more elegant solution?

2reactions
levijacksoncommented, Oct 27, 2015

Expanding on the post above… for touch events the touch.clientX and touch.clientY may not be accurate if the map is not full screen. When I tried the above code the coordinates were off by a bit. I took a look at the way Leaflet figures out the coordinates from event data in L.DomEvent. getMousePosition() and replicated the logic with touch events.

Instead of doing

touch = e.touches[0]
containerPoint = L.point(touch.clientX, touch.clientY)

I did

var touch = e.touches[0],
    rect = this._container.getBoundingClientRect(),
    lat = touch.clientX - rect.left - this._container.clientLeft,
    lng = touch.clientY - rect.top - this._container.clientTop,
    containerPoint = L.point(lat, lng),
Read more comments on GitHub >

github_iconTop Results From Across the Web

How to bind 'touchstart' and 'click' events but not respond to ...
First one has to make ie. the body element track touch events: $(document.body).touchOrMouse('init');.
Read more >
Map click events to touch events in jQuery - Coderwall
To map click events to "touch events", I put together this based on the ... /how-to-bind-touchstart-and-click-events-but-not-respond-to-both.
Read more >
touchstart Event - W3Schools
The touchstart event occurs when the user touches an element. Note: The touchstart event will only work on devices with a touch screen....
Read more >
How to bind 'touchstart' and 'click' events but not respond to both
The touchstart event occurs when the user touches an element. But a click event is fired when the user clicks an element.
Read more >
support for on('touchstart') for map.on events? - Google Groups
So the first part of the code saves the lat/long of the last mousedown event, and then hammertime uses that to detect a...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found