Чому Swipe Actions у списку ламаються на реальних даних
Swipe actions на демонстраційному наборі даних працюють передбачувано: короткі рядки, рівний ритм, жодної фонової синхронізації. На реальному списку все інакше — він довгий, прокручується й оновлюється.
Вертикальне зміщення розпізнається раніше за горизонтальне, жест переходить у прокручування, і свайп по елементу списку не спрацьовує або спрацьовує через раз. Людина перестає шукати дію і йде в контекстне меню, яке ви спеціально прибирали.
Конфлікт жестів і прокручування — лише перша частина. Якщо поріг задано абсолютним зміщенням у точках, а не часткою ширини рядка, на компактних екранах картка розкривається від випадкового дотику під час прокручування.
Виходить хибне спрацьовування дії, до того ж користувач помічає його вже після того, як відпустив палець, — і трактує як зламаний застосунок. Поріг у частках ширини й розділення фаз «зсув» і «підтвердження» прибирають цей клас відмов.
Найдорожче обходиться третя ситуація: список оновлюється під час жесту. Надійшла відповідь від сервера, підвантажилася наступна сторінка, змінився порядок сортування — і розкрита картка переміщується на іншу позицію.
Якщо стан прив'язано до індексу рядка, а не до його ідентифікатора, дія застосовується до чужого об'єкта: видаляється не той запис, іде не той лист. Помилка тиха, відкат вимагає окремого розгляду із втратою даних.
Звідси й вимоги: єдиний розпізнавач напрямку з явним пріоритетом, прив'язка стану до ідентифікатора елемента, поріг у частках ширини й блокування перебудови списку, поки жест не завершено. Розбираємо, як це закривається на кожному рівні — від обробки дотиків до моделі даних.
Що змінюється в застосунку після грамотної жестової механіки
Жестова механіка в списку — це бюджет часу на часті операції та передбачуваність поведінки, а не прикраса.
Коли свайп прикручують поверх готового списку, ламаються три речі: конфлікт із вертикальним прокручуванням, обрізання рядків на різній ширині контенту й скасування замість відкату. Тому на прийманні ми перевіряємо ефект за конкретними пунктами.
- Швидкість частих операцій. Видалення, архівація, «прочитано» й нагадування виконуються одним рухом, без входу в картку: замість трьох-п'яти натискань — одне. На довгій сесії, де таких дій десятки, різниця відчутна.
- Зменшення частки помилкових видалень. Необоротну дію закріплено лише за повним свайпом, поріг спрацьовування задано в частках ширини екрана й підкріплено вікном скасування. Випадкові видалення зникають, навмисні залишаються швидкими.
- Стійкість списку під час зростання даних. Зміщення жесту обчислюється від пальця, а не від позиції елемента, тому відгук однаковий і на сотні рядків, і на десятках тисяч — стан не «залипає» під час перевикористання комірок.
- Передбачуваність для користувача. Поріг, скасування при поверненні в початкову точку й розведення із системним «назад» зафіксовано як правило. Один рух дає один результат на всіх екранах.
- Узгодженість із платформою. Напрямки свайпів і порядок дій збігаються з гайдлайнами — Material Design для Android, системні конвенції для iOS. Навчання механіці не потрібне.
- Спостережуваність після релізу. Події жесту, скасування й відкату йдуть в аналітику, тому набір дій і пороги правляться за даними, а не за думкою.
Варіанти реалізації Swipe Actions: нативна, гібридна, власна
Вибір підходу до свайп-дій визначається не смаком, а тим, скільки поведінки віддає сама платформа і скільки доводиться дописувати вручну. Три робочі варіанти різняться трудомісткістю, стійкістю на різних системах і тим, як жести поводяться в конфліктних сценаріях.
| Варіант | Коли підходить | Обмеження |
|---|---|---|
| Нативна механіка списку | Однотипні рядки, 1–2 дії, стандартна поведінка | Набір дій і анімацій задає платформа, оформлення свайпу майже не налаштовується |
| Гібрид: нативні списки + власний шар жестів | Потрібні свої пороги спрацьовування, 3+ дії, часткове закріплення рядка | Потребує синхронізації з прокручуванням і явного розв'язання конфліктів жестів |
| Власний шар поверх однорідного списку | Вкладені жести, нестандартна фізика, однакова поведінка на обох системах | Віртуалізація, доступність і сумісність з оновленнями системи — на нашій стороні |
Що змінюється на рівні платформ
Системний жест повернення біля краю екрана забирає частину ширини під себе — свайп-дію доводиться зміщувати або вимагати довшого протягування. Усередині горизонтальних каруселей жест треба розводити по осях, інакше рядок починає «тремтіти» під час вертикального прокручування.
Окрема стаття — доступність: у кожної дії має залишитися альтернативний спосіб виклику, що не потребує жесту. На розкладках справа наліво напрямок свайпу дзеркалиться, і це закладається в логіку відразу, а не патчем після релізу.
Режим вибираємо за кількістю дій у рядку, вимогою єдиної поведінки на обох системах і обсягом списку: де вистачає нативної механіки — не пишемо власний шар.
Етапи впровадження жестів у список, що вже працює
Список уже працює: його прокручують, тапають по рядках, тягнуть вниз для оновлення. Жести лягають поверх готової поведінки — спочатку фіксуємо, що не можна зламати, і лише потім проєктуємо схему спрацьовування.
- Аудит списку й поточних жестів. Інвентаризуємо типи рядків і все, що вже реагує на дотик: прокручування, тап, довге натискання, протягування вниз. Окремо позначаємо конфліктні зони — вкладені кнопки, каруселі та поля введення всередині рядка.
- Схема жестів і правила спрацьовування. Для кожного напрямку задаємо дію, поріг у частках ширини рядка, поведінку при неповному русі й повернення назад. Поки палець іде по вертикалі, горизонтальний жест не починається.
- Стан рядка. Вміст отримує єдину обгортку, відкритим може бути лише один рядок, дії ховаються під час прокручування. Жест перестає залежати від типу рядка й не ламається під час оновлення даних.
- Реалізація й доступність. До жесту додаємо рівнозначний шлях без нього — пункт у меню рядка, щоб функція залишилася доступною тим, кому свайп незручний.
- Перевірка на реальних даних. Проганяємо повний обсяг: довгі та порожні рядки, крайні позиції, десятки тисяч елементів, оновлення списку прямо під час жесту. Рахуємо частку хибних спрацьовувань під час прокручування й час відгуку.
- Передача й навчання команди. Залишаємо документ зі схемою жестів, правила додавання нових типів рядків і розбір типових помилок — команда розширює список далі, не переробляючи основу.
Комплект постачання: схема жестів, розмітка, регламенти
Після здачі список не залишається «чорною скринькою»: у вашої команди є комплект, за яким жест swipe actions, стани рядка й поведінка списку відтворюються без нас.
Усе описано в термінах розробника: які жести розпізнаються, у якому стані рядка вони активні, що відбувається під час скасування й повторного свайпу, де межа з вертикальним прокручуванням.
- Схема жестів і станів списку — карта переходів від спокою до часткового й повного зсуву, пороги спрацьовування, поведінка при кількох відкритих рядках.
- Правила розмітки й токени станів — стилі, відступи та кольори для відкритого, закритого й заблокованого рядка, щоб новий рядок успадковував поведінку списку, а не збирався заново.
- Правила доступності дій — мінімальна зона дотику, виклик дії без жесту, порядок для програми читання з екрана, підписи кнопок.
- Регламент правок і підтримки — як додати дію, змінити поріг або іконку, що робити при конфлікті із системним жестом повернення.
- Інструкція для команди — покроковий сценарій: додати рядок, підключити дію, перевірити на пристрої, оновити документацію.
- Документація по списку — єдиний файл зі станами, обмеженнями й відомими винятками, щоб ревʼю не перетворювалося на листування.
Комплект розрахований на те, що через півроку правку робить ваш розробник, а не автор жесту. Якщо регламент застаріває швидше за код, оновлюємо його разом зі змінами — інакше документація розходиться з реальною поведінкою списку.
Кейс: список операцій із жестами — від прототипу до релізу
До впровадження
У застосунку для керування заявками список операцій працював на миттєвому свайпі: рух пальця одразу запускав видалення або зміну статусу, без підтвердження й без повернення.
Зона жесту перетиналася з вертикальним прокручуванням, тому під час швидкого прокручування користувачі зривали рядок і видаляли запис випадково. Частка помилкових дій сягала 3,5% від усіх жестів у списку, а підтримка щомісяця розбирала звернення про відновлення видаленого.
Що змінили
Ми розвели жест і прокручування за порогом зміщення: рядок тягнеться лише після впевненого горизонтального руху, вертикальний скрол залишається пріоритетним.
Свайп перестав виконувати дію миттєво — він розкривав кнопки за домовленостями Material Design, сама дія спрацьовувала після відпускання й підтверджувалася коротким вікном скасування.
Типову операцію — закрити заявку — тепер можна виконати прямо зі списку, не відкриваючи картку: час на дію скоротився з 9 до 2 секунд, глибина сценарію — з чотирьох переходів до одного.
Що стало
Частка помилкових дій у списку впала до 0,4%, хибні видалення перестали доходити до бази — відкат доступний прямо в рядку, відновлення через підтримку більше не потрібне. Потік звернень щодо роботи зі списком скоротився в шість разів.
Жестами почали користуватися активніше: частка операцій через свайп зросла з 12% до 41%, бо сценарій став коротшим і передбачуванішим.
Чим відрізняється дія по елементу від дії по всьому рядку
Режими різняться тим, де починається дотик і до якого об'єкта прив'язано жест. Жест по елементу рядка спрацьовує всередині конкретного елемента керування — іконки, перемикача, мініатюри — і виконує часткову дію над елементом: позначити, закріпити, відкрити картку.
Жест по всьому рядку захоплює комірку цілком і запускає повну дію над записом — видалення, архівування, зміну статусу.
| Режим | Що змінює | Ризик випадкового спрацьовування | Коли підходить |
|---|---|---|---|
| Жест по елементу рядка | Часткова дія над елементом | Низький: ціль дрібна, намір явний | Часті легкі операції |
| Жест по всьому рядку | Повна дія над записом | Високий: конфлікт із прокручуванням і поверненням | Масові операції |
| Жест по рядку з підтвердженням | Повна дія над записом після дотягування | Середній: зайвий крок замість відкату | Необоротні операції |
Головний ризик жесту по всьому рядку — конкуренція з прокручуванням списку й системним поверненням від краю екрана. При малому порозі список смикається на кожному прокручуванні, при великому користувач не доводить жест і вважає функцію неробочою.
Поріг задають у частках ширини комірки, додають тактильний відгук на старті й анімацію дотягування, а необоротну дію відправляють після підтвердження.
Часткова дія над елементом безпечніша, але впирається в площу: у щільному рядку дрібні цілі конкурують між собою й програють вимогам доступності.
Звідси робоча схема — повну дію над записом тримають за підтвердженням або багатокроковим скасуванням, а часткові жести залишають для частих і легких операцій.
Доступність, конфлікти й відкати: про що запитують до старту
До старту виникають одні й ті самі сумніви: чи не зламає свайп доступність, що робити тим, хто жестами не користується, як відкотити випадкову дію й що побачать користувачі на старих версіях застосунку.
Принцип простий: жест — прискорення, а не єдиний шлях. Кожна дія зі свайпу дублюється в контекстному меню за довгим натисканням і в картці елемента, тому весь сценарій проходиться й без жестів.
Жест доступний лише зрячим і спритним користувачам?
Ні. Пункти свайпу реєструються як доступні дії елемента списку, тому екранний диктор зачитує їх у меню дій, а не мовчить про них. Задаємо зрозумілі підписи, тактильний відгук і поріг спрацьовування, який не плутає жест із прокручуванням. Орієнтир — WCAG: у будь-якої дії є альтернатива без жесту.
Як відкотити дію, якщо свайпнули випадково?
Список оновлюється відразу, але операція йде в чергу зі скасуванням: кілька секунд доступна кнопка «Повернути», а до підтвердження стан зберігається локально.
Якщо запит до сервера не пройшов, елемент повертається на попереднє місце сам — без перезавантаження списку й порожніх рядків.
Що побачать користувачі на старих версіях застосунку?
Нічого критичного. Свайп вмикається флагом на стороні сервісу й не змінює формат даних, тому старі збірки працюють як раніше: жест просто не з'являється, дії залишаються доступні через меню.
Оновлення викочується поступово, без обов'язкового завантаження нової версії з магазину застосунків.
Ці чотири питання перевіряємо на етапі проєктування, до коду. Опишіть задачу — повернемося з оцінкою та планом.Обговоримо задачу: схема жестів і план робіт
Щоб оцінка термінів була чесною, а не «приблизно тиждень», нам потрібно побачити поточний список очима коду: чим він рендериться, де зберігається стан рядка, які жести й меню вже перехоплюють дотики. Опишіть це у вільній формі — далі розбір іде на нашій стороні.
У відповідь надсилаємо схему жестів під ваш продукт: напрямки свайпів, пороги спрацьовування, поведінку рядка під час скасування, розв'язання конфліктів із прокручуванням і бічним меню.
Разом із нею — план робіт і етапи, щоб рішення ухвалювалося до першого рядка коду, та оцінку термінів впровадження з окремим запасом на нестандартні місця.
- Схема жестів під продукт: що йде на свайп вліво та вправо, де поріг, як працює скасування.
- Розбір поточного списку: компонент рендерингу, зберігання стану рядка, уже зайняті жести й контекстні меню.
- План робіт і етапи: підготовка розмітки, підключення жестів, доступність, перевірка на реальних пристроях.
- Оцінка термінів впровадження за етапами — окремим рядком ідуть нестандартні випадки й доопрацювання.
- Перелік перевірок: свайп без розкриття дії, швидкий свайп, свайп під час прокручування, скасування на півшляху.
- Список екранів і місць, де новий жест конфліктує з поточною поведінкою списку.
Опишіть задачу по списку: що за екран, скільки типів рядків, які дії потрібні. Повернемося зі схемою жестів, етапами та оцінкою термінів впровадження.







