دکمه‌ی تأییدِ لغزندهSlide Commit

دکمه‌ای که برای تأیید باید دستگیره‌اش رو تا انتها بکشی؛ نتیجه با چرخنده و بعد قرصِ تأیید یا رد نشون داده می‌شه.

محمدجواد

ساخته شده توسط محمدجواد

سازنده فارسی‌فای، بچه دولوپر

وابستگی‌ها

motion

نوع تعامل

دستگیره رو به کنار بکش. اگه کم بکشی، با فنر برمی‌گرده و به دیوارِ خانه می‌خوره؛ اگه تا انتها برسونی، تأیید می‌شه. با صفحه‌کلید: کلیدِ راست یا بالا جلو می‌بره (ده‌یکِ مسیر با هر فشار) و `End` مستقیم تأیید می‌کنه؛ کلیدِ چپ یا پایین عقب می‌بره و `Home` یا `Escape` به اول برمی‌گردونه.

پراپ‌ها

گزینه‌هایی که می‌تونی به کامپوننت بدی؛ ستاره‌دارها اجباری‌اند.

label
ReactNodeپیش‌فرض: "برای پرداخت بکش"

نوشته‌ی وسطِ قرص؛ با کشیدن پاک می‌شه.

doneLabel
ReactNodeپیش‌فرض: "پرداخت شد"

نوشته‌ی کنارِ تیک، بعد از تأیید.

errorLabel
ReactNodeپیش‌فرض: "پرداخت انجام نشد"

جانشینِ نوشته‌ی راهنما، با رنگِ خطر، بعد از ردِ شدن.

onConfirm
() => void | Promise<unknown>

وقتی دستگیره به انتها می‌رسه صدا زده می‌شه. اگه Promise برگردونه، چرخنده نشون داده می‌شه.

onDone
() => void

وقتی قرصِ تمام‌شده باز می‌شه صدا زده می‌شه.

onError
(reason: unknown) => void

با دلیلِ ردِ شدن صدا زده می‌شه؛ وگرنه کامپوننت خودش می‌بلعش.

نصب

۱. این آدرس رو یک‌بار توی components.json بذار تا shadcn مخزن فارسی‌فای رو بشناسه.

components.jsonjson
{
  "registries": {
    "@farsify": "https://farsify.ir/r/{name}.json"
  }
}

۲. بعد با دستورِ زیر کامپوننت رو نصب کن.

npx shadcn@latest add @farsify/slide-commit

پیش‌نیاز: Tailwind CSS v4 و صفحهٔ راست‌به‌چپ dir="rtl".

نمونه

slide-commit.tsxtsx
"use client";

import SlideCommit from "@/components/farsify/slide-commit";

export function PayButton() {
  return (
    <SlideCommit
      label="برای پرداخت بکشید"
      doneLabel="پرداخت شد"
      errorLabel="پرداخت انجام نشد"
    />
  );
}

// با Promise: چرخنده نشان داده می‌شود، بعد از resolve
// قرصِ سبز باز می‌شود و با reject تکان می‌خورد
<SlideCommit
  label="برای حذف بکشید"
  doneLabel="حذف شد"
  errorLabel="حذف انجام نشد"
  successColor="#22c55e"
  dangerColor="#e5484d"
  onConfirm={async () => {
    const res = await fetch("/api/delete", { method: "POST" });
    if (!res.ok) throw new Error("حذف نشد");
  }}
  onDone={() => router.refresh()}
  onError={(reason) => console.error(reason)}
/>

// موفقیتِ بی‌درنگ: بدون Promise، بی‌چرخنده و بی‌مکث
<SlideCommit
  label="برای تأیید بکشید"
  width={220}
  height={48}
  radius={12}
  holdMs={0}
  onConfirm={() => setDone(true)}
/>

نکته‌ها

  • اگه `onConfirm` یه Promise برگردونه، چرخنده نشون داده می‌شه — همین راهِ درستِ وصل‌کردن به شبکه‌ست. اگه خطا بده، دستگیره تکون می‌خوره و برمی‌گرده؛ پس کاربر می‌فهمه نشد، بدونِ این‌که صفحه‌ت پیامِ جدا نشون بده.
  • چرخنده عمداً کمینه ۳۰۰ میلی‌ثانیه می‌مونه. بدونِ اون، پاسخِ سریع باعث می‌شد یه قاب بپره و ناپدید شه و کاربر «در حال انجام» رو اصلاً نبینه.
  • برچسب‌ها رابطِ کاربری‌ان، نه داده — روی خودِ قرص دیده می‌شن، `aria-label` می‌شن و توی ناحیه‌ی زنده اعلام می‌شن. پس فارسی بمون؛ فقط اگه برچسبِ خودت رو می‌دی عوضش کن.
  • برخلافِ بیشترِ کامپوننت‌های راست‌به‌چپ، این‌جا **هیچ‌چیز آینه نمی‌شه و نباید بشه**: همه‌ی هندسه فیزیکیه و فلش هم با جهتِ حرکتِ دستگیره هم‌جهته. پس کلیدِ راست یعنی «جلوتر»، عیناً مثلِ جهتِ کشیدن.
  • `holdMs={0}` قرصِ تمام‌شده رو نگه می‌داره تا کامپوننت از نو سوار شه — برای وقتی که جای دیگه‌ای نتیجه رو نشون می‌دی.

مجوز

کد بعد از نصب مالِ خودته؛ هر تغییری خواستی بده و توی پروژه‌ی خودت نگهش دار. برای پروژه‌های شخصی و تجاری آزاده، حتی اگه کدت بسته باشه. فقط اسم و لینک فارسی‌فای رو یه جا توی پروژه نگه دار.