You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
4.0 KiB
4.0 KiB
هدف
اسلاید بین سوالات مثل ریلز اینستاگرام / شورتز یوتیوب: محتوا 1:1 با انگشت حرکت کند، رها کردن بر اساس سرعت (flick) یا مسافت یا commit به بعدی/قبلی یا برگشت، rubber-band در دو انتها، و انیمیشن قابل مقطوعسازی (grab mid-animation).
تغییرات — فقط src/components/Componentes/question-snap-list.tsx
1. لایهی درگ با دنبال کردن انگشت (بدون re-render در هر فریم)
- در
touchstart: ثبت نقطه/زمان شروع + ارتفاع کانتینر. اگر لمس روی کنترلهای تعاملی شروع شود (input, textarea, select, [contenteditable], [data-snap-drag-ignore]) درگ فعال نمیشود تا با تایپ/اسلایدر تداخل نکند. - در
touchmoveبعد از عبور از آستانه ~۱۰px: اعمال مستقیمtransformروی سه پنل (فعال، بعدی، قبلی) از طریق ref (بدون state ریاکت) → 60fps:- فعال:
translateY(-offset)— بالا میرود با انگشت - بعدی:
translateY(height - offset)— از پایین بهصورت پنل کامل وارد میشود - قبلی:
translateY(-height - offset)— از بالا وارد میشود
- فعال:
- Rubber-band: در سوال اول/آخر، آفست با ضریب مقاومت 0.4 فشرده میشود.
- محاسبهی velocity با میانگین متحرک نمایی روی نمونههای حرکت.
2. تصمیم رها کردن (touchend)
- commit به بعدی/قبلی اگر: مسافت > 30% ارتفاع یا |velocity| > 0.55 px/ms (flick).
- وگرنه spring-back با انیمیشن
cubic-bezier(0.22,1,0.36,1)~340ms. - هنگام commit: همان callback های فعلی (
onQuestionExit,onQuestionTransition) +setActiveIndexفراخوانی میشود؛ انیمیشن inline ادامه پیدا میکند و بعد از پایان، style های inline پاک میشوند تا state کلاسی بدون پرش تحویل داده شود.
3. قابل مقطوعسازی
- اگر وسط انیمیشن snap دوباره انگشت بگذارد: موقعیت فعلی با
getComputedStyle + DOMMatrixخوانده و فریز میشود و درگ از همان نقطه ادامه مییابد (مثل ریلز).
4. حذف پیشنمایشهای ۱۱۰px (peek)
- برای اسلاید پنل کامل ریلز-مانند، پنلهای قبل/بعد در حالت سکون کاملاً خارج از دید (
translate-y-full/-translate-y-full) قرار میگیرند و wrapper هایmax-h-[110px] overflow-hiddenحذف میشوند. خودِ درگ جای affinity بصری را میگیرد. - wheel دسکتاپ سرجایش میماند و حالا بهصورت اسلاید کامل انیمیت میشود (transition کلاس موجود).
5. حفظ تمام رفتارهای فعلی
حفاظ dropdown-open (شیت باز = بدون درگ)، فوکوس خودکار input سوال فعال، init روی اولین سوال بیپاسخ، alignTop، اسپیسر 20%، inert/aria، touchcancel → برگشت، چند-لمسی → نادیده.
خارج از scope
- تغییر رفتار wheel/کیبورد دسکتاپ، مرورسازی horizontal، تغییر auto-focus.
- شیت کد کشور phone (همان 68svh) — طبق خواسته فقط QuestionSheet تغییر کرد.
راستیآزمایی
npx vitest run+npx tsc --noEmit(یا biome).- تست دستی در مرورگر با viewport موبایل: درگ با ماوس (شبیهسازی touch)، wheel، اسکرینشات قبل/بعد رها کردن، بررسی مرز rubber-band در اولین/آخرین سوال، باز کردن شیت nationality (تغییر 82svh قبلی) و فوکوس input متنی (حرکت به بالا با کیبورد).