Touch события и жесты

Touch-события в Svelte являются важной частью взаимодействия с мобильными устройствами, а также с сенсорными экранами. В отличие от стандартных событий мыши, такие как click, mouseover и другие, события касания обеспечивают управление взаимодействием через сенсорные экраны, позволяя отслеживать касания, свайпы, удержания и другие действия пользователя.

Svelte предлагает простой и эффективный способ работы с touch-событиями, без необходимости в сложной обработке этих событий через JavaScript. В этом разделе рассмотрим основные типы touch-событий, их использование и реализацию жестов.

Основные типы touch-событий

Svelte поддерживает стандартные события для работы с касаниями на устройствах с сенсорными экранами. Эти события включают:

  • touchstart: срабатывает при начале касания экрана.
  • touchmove: срабатывает при движении пальца по экрану после начала касания.
  • touchend: срабатывает при окончании касания, когда палец убран с экрана.
  • touchcancel: срабатывает, когда касание было отменено системой, например, при изменении контекста.

Эти события могут быть использованы для отслеживания различных типов взаимодействий, от простых касаний до сложных жестов, таких как свайпы и увеличение/уменьшение масштаба.

Обработка touch-событий в Svelte

В Svelte обработка touch-событий происходит в рамках компонента с использованием директивы on:event, которая автоматически связывает событие с обработчиком.

Пример использования touchstart:

<script>
  let message = 'Пока не коснулись экрана';
  
  function handleTouchStart(event) {
    message = 'Коснулись экрана!';
  }
</script>

<div on:touchstart={handleTouchStart}>
  {message}
</div>

В данном примере при касании экрана сообщение обновляется, информируя пользователя о начале взаимодействия.

Работа с координатами касания

Каждое touch-событие предоставляет объект события, который содержит информацию о положении касания. Для получения координат касания используется свойство touches, представляющее собой список всех касаний в момент события. Для работы с единичным касанием можно использовать touches[0].

Пример с использованием координат:

<script>
  let touchCoordinates = { x: 0, y: 0 };
  
  function handleTouchMove(event) {
    const touch = event.touches[0];
    touchCoordinates = { x: touch.clientX, y: touch.clientY };
  }
</script>

<div on:touchmove={handleTouchMove}>
  X: {touchCoordinates.x}, Y: {touchCoordinates.y}
</div>

В этом примере при движении пальца по экрану на экран выводятся текущие координаты касания.

Управление многократными касаниями

Если на экране происходит несколько касаний одновременно, события touchstart, touchmove, touchend будут содержать несколько точек контакта. Для этого Svelte позволяет работать с массивом касаний, доступным через touches.

Пример для работы с несколькими касаниями:

<script>
  let touchesInfo = [];

  function handleTouchStart(event) {
    touchesInfo = Array.from(event.touches).map(touch => ({
      identifier: touch.identifier,
      x: touch.clientX,
      y: touch.clientY
    }));
  }
</script>

<div on:touchstart={handleTouchStart}>
  {#each touchesInfo as touch}
    <div>Касание {touch.identifier}: X: {touch.x}, Y: {touch.y}</div>
  {/each}
</div>

Здесь при каждом новом касании на экране будет отображаться информация о его позиции.

Жесты и их реализация

Для реализации жестов в Svelte, таких как свайпы, увеличение/уменьшение масштаба или повороты, необходимо отслеживать несколько touch-событий в последовательности. Рассмотрим, как можно реализовать свайп.

Свайпы

Свайп — это жест, при котором пользователь проводит пальцем по экрану в одном из направлений. Для его отслеживания необходимо вычислить разницу между начальной и конечной позицией касания по оси X или Y.

Пример реализации свайпа:

<script>
  let swipeDirection = '';

  let touchStartX = 0;
  let touchStartY = 0;

  function handleTouchStart(event) {
    touchStartX = event.touches[0].clientX;
    touchStartY = event.touches[0].clientY;
  }

  function handleTouchEnd(event) {
    const touchEndX = event.changedTouches[0].clientX;
    const touchEndY = event.changedTouches[0].clientY;

    const diffX = touchEndX - touchStartX;
    const diffY = touchEndY - touchStartY;

    if (Math.abs(diffX) > Math.abs(diffY)) {
      swipeDirection = diffX > 0 ? 'Свайп вправо' : 'Свайп влево';
    } else {
      swipeDirection = diffY > 0 ? 'Свайп вниз' : 'Свайп вверх';
    }
  }
</script>

<div on:touchstart={handleTouchStart} on:touchend={handleTouchEnd}>
  {swipeDirection}
</div>

В этом примере свайп по горизонтали или вертикали определяется по разнице между начальной и конечной позицией касания. Это позволяет отслеживать направления свайпа и выводить соответствующее сообщение.

Масштабирование и вращение

Масштабирование и вращение являются сложными жестами, которые обычно требуют использования двух пальцев. Для отслеживания этих жестов необходимо вычислять изменения расстояния между двумя точками (для масштабирования) или угол между ними (для вращения).

Пример реализации масштабирования:

<script>
  let scale = 1;
  let startDistance = 0;

  function handleTouchStart(event) {
    if (event.touches.length === 2) {
      startDistance = Math.hypot(
        event.touches[1].clientX - event.touches[0].clientX,
        event.touches[1].clientY - event.touches[0].clientY
      );
    }
  }

  function handleTouchMove(event) {
    if (event.touches.length === 2) {
      const currentDistance = Math.hypot(
        event.touches[1].clientX - event.touches[0].clientX,
        event.touches[1].clientY - event.touches[0].clientY
      );
      scale = currentDistance / startDistance;
    }
  }
</script>

<div
  on:touchstart={handleTouchStart}
  on:touchmove={handleTouchMove}
  style="transform: scale({scale});"
>
  Масштабирование
</div>

В этом примере вычисляется начальное расстояние между двумя касаниями при touchstart и обновляется коэффициент масштабирования при движении пальцев.

Заключение

Touch-события в Svelte позволяют реализовать широкий спектр взаимодействий на мобильных устройствах и сенсорных экранах. Используя стандартные события и работу с координатами касаний, можно реализовывать как простые действия, такие как касания и движения, так и более сложные жесты, включая свайпы, масштабирование и вращение. Простота интеграции touch-событий в Svelte и высокая производительность делают этот подход эффективным для создания современных мобильных интерфейсов.