Home › Forums › JavaScript › Touch device ghost click triggers on different element › Reply To: Touch device ghost click triggers on different element
Okay, I think I finally got to the bottom of this. There are two issues crossing each other. The first one is the more generally known ghost clicks, these seem to be handled nicely from where I got so far. The other issue is very Android specific and hard to describe. After a custom (click) event that deals with both touch and mouse and then hiding the element in question, the emulated mouse events caused by touch devices are triggered on the element that was underneath it. And not on the element itself. This is clearly a bug that needs an approach of it’s own – I chose to use elementFromPoint
to determine which element is underneath and temporarily disable pointer events on it. Strangely enough links still get highlighted because of an emulated hover
effect now and then but I can live with that.
So I’m sending some extra data with the custom page:tap
event (did I ever mention how excellent this part of jQuery is?), namely the touch coordinates:
var nub = $('html'), swiftClick = function(aim) {
$(bud).on('mousedown touchstart', aim, function(e) {
if (e.type == 'mousedown' && e.which != 1) return;
var mean = $(e.currentTarget);
if (e.type == 'touchstart') {
var feel = e.originalEvent.touches[0],
region = [feel.screenX, feel.screenY];
}
mean.one('mouseup touchend', function(e) {
var hit = nub.hasClass('punch');
if (e.type == 'touchend' && !hit) nub.addClass('punch');
else if (hit) return;
mean.trigger({type: 'page:tap', put: region});
});
}).on('click', aim, function() {
if (!nub.hasClass('punch')) return;
nub.removeClass('punch');
return false;
});
}
Also troublesome on Android, nothing but screenX
and screenY
did the trick.
Next step is to listen to the custom event, check the coordinates and “silence” the element below if it is a link (closing the modal would trigger a redirect before):
var goal = '#anelement';
swiftClick(goal);
$(goal).on('page:tap', function(e) {
if (!e.put) return;
var below = document.elementFromPoint(e.put[0], e.put[1]),
sample = $(below).closest('a');
if (!sample) return;
sample.addClass('silent');
setTimeout(function() {
sample.removeClass('silent');
}, 500);
});
.silent {
pointer-events: none;
}
Very circumventive but that’s old Android for ya…