Есть ли способ TouchEndInside в мобильном сафари?
Я пытаюсь определить, выполняет ли пользователь касание в мобильном сафари для веб-приложения iPhone. Пока что мне не удалось. Событие touchend срабатывает независимо от того, где происходит событие касания, и я не могу понять, что цель изменилась в аргументе события.
Может кто-нибудь указать мне правильное направление о том, как захватить событие touchendinside (против touchendoutside), используя javascript?
$('a.arrow').bind('touchend',function(e) {
console.log($(e.srcElement)); //both of these always return the same element
console.log($(e.toElement)); //both of these always return the same element
});
2 ответа
Я нашел статью, опубликованную Google, в которой указано, как определить, находится ли каскад внутри или снаружи. Основной трюк:
- Имейте 3 обработчика: один на touchstart, touchmove и touchend.
- touchstart: сохранить (x,y) координаты касания
- перемещение по касанию: убедитесь, что касание не сдвинулось на определенное количество пикселей по любой оси, и если это так, прекратите отслеживать касание.
- touchend: если вы все еще отслеживаете его, он "внутри"; если нет, то это "снаружи".
Вы всегда можете сделать более сложным, используя фактические границы цели и т. Д., Но для большинства приложений этого, вероятно, достаточно.
@ Крис Р. Доннелли на месте. Вам нужно использовать комбинацию трех событий js (touchstart
, touchmove
а также touchend
) эффективно создать свой собственный распознаватель жестов.
Подход Google, вероятно, действительно хороший путь. Я еще не пробовал.
Вот базовый пример слушателя "touch up inside" для Mobile Safari, который прослушивает только js-события на целевом элементе. Он будет игнорировать любое касание, возникающее за пределами элемента, любое касание, которое заканчивается за пределами элемента, и любое касание, которое перетаскивается внутри элемента. Это не обрабатывает клики (вы должны добавить это, если вы поддерживаете рабочий стол тоже).
<script type="text/javascript">
document.getElementById("yourElementId").addEventListener('touchstart', touchstart, false);
document.getElementById("yourElementId").addEventListener('touchmove', touchmove, false);
document.getElementById("yourElementId").addEventListener('touchend', touchend, false);
var touchStartCoord = null;
function touchstart (e) {
touchStartCoord = {x: e.touches[0].pageX, y: e.touches[0].pageY};
return true;
};
function touchmove (e) {
if (touchStartCoord != null)
{
var tolerance = 10.0;
if (Math.abs(e.touches[0].pageX-touchStartCoord.x) > tolerance || Math.abs(e.touches[0].pageY-touchStartCoord.y) > tolerance)
{
// moved too far, cancels event for this touch
touchStartCoord = null;
}
}
return true;
};
function touchend (e) {
if (touchStartCoord != null)
{
window.location.href = "http://geospike.com/";
return true;
}
};
</script>
Если вы хотите поддерживать несколько элементов, вы можете обернуть их повторно.