دیزاین سیستم الگوهای کاربری

الگوهای کاربری

کامپوننت‌ها «چه شکلی» را پاسخ می‌دهند؛ الگوها «چطور کار می‌کند» را. هر الگو یک مسئله تکرارشونده واقعی محصول را با ترکیبی از کامپوننت‌ها حل می‌کند — و در اپ مرجع همین الان در حال اجراست.

۱کلاس‌های پنجره — ناوبری واکنش‌گرا

یک DOM، سه چیدمان ناوبری بر اساس عرض نمایشگر (کلاس‌های پنجره MD3). هیچ نسخه جداگانه‌ای برای موبایل وجود ندارد؛ فقط CSS عوض می‌کند.

compact — زیر ۶۰۰px
medium — ۶۰۰ تا ۸۳۹
expanded — ۸۴۰ و بالاتر
کلاسعرضناوبرینمای اولیهایجاد
compact<۶۰۰نوار پایین ۵تایی + FAB + کشوی بیرون‌ از صفحهبرنامه (فشرده)فقط FAB و کلید N
medium۶۰۰–۸۳۹ریل آیکونی ۸۰px + FAB + کشو از دکمه منوبرنامهFAB + ریل
expanded+≥۸۴۰سایدبار دائمی ۲۶۴px (سمت راست) + دکمه ایجاد در سایدبارماهدکمه سایدبار + کلید N

بایدر

  • نمای فعال و تاریخ جاری در localStorage ذخیره و بعد از بارگذاری بازیابی می‌شود.
  • عمق لایه ناوبری: نوار پایین/ریل → کشو/سایدبار → دیالوگ — هر عمق فقط یک‌بار.

نبایدر

  • هم‌زمان نوار پایین و ریل؛ یا سایدبار باز و کشو روی هم.
  • مخفی‌کردن اکشن ایجاد در هیچ کلاسی — فقط جایش عوض می‌شود.

۲پیش‌نمایش سپس ویرایش

کلیک روی هر رویداد، وظیفه یا تقویم، دیالوگ را در حالت نمایش باز می‌کند: همه داده‌ها فقط‌خواندنی، سریع‌الاسکن، بدون خطر تغییر تصادفی. کاربر با دکمه «ویرایش» به فرم می‌رسد. مسیر «ایجاد» مستقیم به فرم می‌رود — پیش‌نمایش برای موجودهاست.

گاممحتوااکشن‌ها
۱ · کلیکروی چیپ رویداد، ردیف وظیفه، نتیجه جستجو یا کارت تقویم
۲ · نمایشعنوان + تاریخ کامل جلالی (تعطیلی/جمعه قرمز) + ساعت یا «تمام‌روز» + تقویم با نقطه رنگ + نوع + مکان + مهمان‌ها + یادداشتحذف (مخرب) · ویرایش (اصلی و تنها)
۳ · ویرایشهمان دیالوگ با فرم پیش‌پر؛ فوکوس روی عنوانذخیره · انصراف · حذف

جابه‌جایی حالت با یک اتریبیوت روی دیالوگ — بدون بستن/بازکردن مجدد:

<div class="dialog" data-mode="view|edit">
  <!-- view: سطرهای فقط‌خواندنی + دکمه ویرایش -->
  <!-- edit: فرم پیش‌پر + ذخیره/انصراف -->
</div>

بایدر

  • در حالت نمایش فقط یک دکمه اصلی («ویرایش»)؛ حذف در سمت مقابل.
  • موتورهای یکسان: Enter = ویرایش، Esc = بستن، تغییر حالت بدون پرش چیدمان.

نبایدر

  • باز شدن مستقیم فرم ویرایش روی کلیک ساده — تغییر تصادفی محتمل است.
  • دو مرحله اضافی: نمایش → «ادامه» → فرم خالی. پیش‌نمایش باید کامل باشد.

۳دیالوگ‌ها، برگه‌ها و منوها

سلسله‌مراتب لایه‌های شناور و قواعد مشترک باز/بسته‌شدن.

لایهابزارچه زمانی
۱ · منو.menuاکشن‌های فرعی یک لنگر — بدون محتوای فرمی
۲ · پاپ‌آور انتخاب تاریخ.dpopزیر قرص تاریخ؛ Esc اول این را می‌بندد، بعد دیالوگ را
۳ · دیالوگ/برگه.dialogایجاد/نمایش/ویرایش رویداد و وظیفه، تعارض‌ها، رزرو
۴ · توست.toastنتیجه عمل — بدون قطع‌کردن جریان

قواعد مشترک

  • — اسکریم ۴۵٪ + بلور ۳px؛ کلیک روی اسکریم = بستن (به‌جز وقتی فرم کثیف است: اول تأیید).
  • — قفل اسکرول بدنه و محبوس‌کردن فوکوس در دیالوگ؛ فوکوس به عنصر محرک برمی‌گردد.
  • — حذفِ قابل‌بازگردانی به‌جای دیالوگ تأیید، توستِ «بازگردانی» می‌دهد — یک گام کمتر.
  • — هم‌زمان فقط یک لایه از هر عمق؛ باز شدن لایه جدید، قبلی را می‌بندد.

۴انتخاب تاریخ جلالی

پاپ‌آور ۲۷۲px که از قرص تاریخ باز می‌شود — همان شبکه ماه، با رفتار کامل تقویمی.

شهریور ۱۴۰۵
شیدسچپج
۱۲۳۴۵۶۷ ۸۹۱۰۱۱۱۲۱۳۱۴
قاعدهجزئیات
لنگر و هالهباز شدن پاپ‌آور، قرصِ تاریخ را با .open روشن نگه می‌دارد — کاربر می‌داند چه چیزی دارد ویرایش می‌شود
ناوبری ماهشورون‌های RTL: «قبلی» سمت راست؛ کلیک روی عنوان = انتخاب ماه/سال سطح بالا
پاورقی«امروز» همیشه؛ «پاک کردن» فقط برای تاریخ‌های اختیاری (موعد وظیفه)
کیبوردفلش‌ها روز به روز جابه‌جا می‌کنند؛ ماه از سرِ هفته که رد شود، ماه عوض می‌شود؛ Esc فقط پاپ‌آور را می‌بندد
اعتبارروشن/تعطیل فقط رنگ است، نه غیرفعال — هر روزی قابل انتخاب است

۵فرم‌ها

ترتیب استاندارد فیلدها و قواعد اعتبارسنجی — از دیالوگ رویداد تا ورود.

قاعدهجزئیات
ترتیب فیلدهااز مهم به جزئی: عنوان ← تقویم ← نوع ← شروع/پایان ← تمام‌روز ← مکان ← مهمان‌ها ← یادداشت
ستون واحدفرم‌ها همیشه تک‌ستونه؛ فقط شروع/پایان دو قرص هم‌عرض در یک سطر گرید ۲تایی
اعتبارسنجیزنده اما بی‌سروصدا: خطا بعد از تعامل کاربر ظاهر می‌شود، نه حین تایپ اول
پیام خطاعلت + راه‌حل: «پایان نمی‌تواند قبل از شروع باشد» — نه «مقدار نامعتبر»
CTAغیرفعال تا اعتبار کامل؛ بعد از ارسال، متن با اسپینر عوض می‌شود و دکمه قفل می‌ماند
ارقامورودی عددی (تلفن، OTP) با direction:ltr + تبدیل ارقام فارسی به لاتین هنگام خواندن (J.en)
Enterدر فرم تک‌فیلدی (تلفن، جستجو) = ارسال؛ در فرم کامل = هیچ (جلوگیری از ثبت تصادفی)

۶استیت‌های داده

هر سطح داده سه استیت دارد و همه باید طراحی شوند — بارگذاری، خالی، خطا.

استیتنمایشقاعده
بارگذاریاسپینر وسط ناحیه؛ شبکه‌های بزرگ اسکلتون‌گونه با سلول‌های سطح ۱کمتر از ۳۰۰ms هیچ‌چیز نشان نده — پرش استیت نریزان
خالیپیام کوتاه + اکشن ایجاد (در جای مجاز): «فعلاً کاری نیست» / «رویدادی در این روز نیست»هر تب و نما رشته خالی مخصوص خودش را دارد؛ هیچ «—» یا باکس خالی
خطاپیام + «تلاش دوباره»؛ لیست‌های مهم تاریخ آخرین موفقیت را نگه می‌دارندخطای شبکه دیتای قبلی را پاک نمی‌کند
همه‌پنهانوقتی همه تقویم‌ها از دید خارج‌اند: راهنمای برگرداندن به‌جای گرید خالیمحتوا باید خودش علت خالی‌بودنش را بگوید

۷همگام‌سازی و تعارض

همگام‌سازی پس‌زمینه‌ای است و وقتی خوب کار می‌کند دیده نمی‌شود.

  • پیش‌فرض ساکت: موفقیت همگام‌سازی نه بنر دارد نه توست. آخرین زمان همگام‌سازی فقط در جایگاه کم‌رنگ تنظیمات.
  • تعارض = تنها استیت پرهیاهو: بنر کهربایی زیر نوار بالا → دیالوگ فهرست تعارض‌ها با عنوان، فیلد تغییرکرده و دو تصمیم: «نگه‌داشتن نسخه این دستگاه» / «بازگردانی نسخه سرور».
  • — تصمیم هر آیتم مستقل است؛ بعد از تصمیم آخرین آیتم، بنر به‌تنهایی جمع می‌شود.
  • — حالت آفلاین: کار بدون وقفه ادامه دارد؛ تعارض‌ها هنگام بازگشت اتصال حل می‌شوند.

۹حالت تاریک

حالت تاریک تعویض توکن است، نه طرح دوم: data-theme="dark" روی ریشه و همه‌چیز خودش درست می‌شود.

قاعدهجزئیات
برندآبی پر کنتراست پایین می‌آید (#8FB4FF) و متن دکمه تیره می‌شود — وارونگی کامل fg/bg در همان قاعده
تعطیلاتقرمز #D41317 در تاریک به #FF8A80 روشن می‌شود تا روی سطح تیره بخواند
رویدادهاپالت ۸رنگی با color-mix روی سطح تیره روشن می‌شود؛ پس‌زمینه چیپ‌ها همان ۱۳٪ رنگ می‌ماند
سایه‌هادر تاریک عمیق‌تر و اسکریم تا ۵۸٪ — عمق باید حفظ شود
ماندگاریانتخاب کاربر در tvm-theme ذخیره و بین همه صفحه‌های وب مشترک است
آزمون شبانه: هر صفحه/کامپوننت جدید باید در هر دو پوسته بازبینی شود — دکمه خورشید/ماه همین مستندات بهترین جای آزمون است، چون همه نمونه‌ها زنده‌اند.

۱۰دسترس‌پذیری و نوشتار رابط

نقشه کیبورد

کلیدعمل
→ / ←ماه بعد/قبل (در RTL جهت‌ها طبیعی تقویم‌اند)
↑ / ↓هفته بعد/قبل در نمای ماه
Tپرش به امروز
Nایجاد رویداد/وظیفه (بر اساس نمای فعال)
/فوکوس روی جستجو
Escبستن به ترتیب عمق: تاریخ‌یاب ← منو ← دیالوگ

حداقل‌های غیرقابل مذاکره

  • — کنتراست متن ≥ ۴٫۵:۱ در هر دو پوسته؛ هاور هرگز متن را کم‌کنتراست‌تر نمی‌کند.
  • :focus-visible حلقه ۲px برند روی هر عنصر قابل فوکوس — بدون حذف outline.
  • — هدف لمسی ≥ ۴۴px؛ دکمه‌های آیکونی همیشه aria-label فارسی دارند.
  • prefers-reduced-motion همه انیمیشن‌ها را خاموش می‌کند؛ پیام با حرکت جابه‌جا نمی‌شود.
  • — نقش‌های ARIA وضعت‌دار: role="checkbox/switch/dialog" + aria-checked.

نوشتار رابط

اصلدرستغلط
روشن و بدون اغراقهمگام‌سازی با خطا مواجه شداوه! یک اتفاق غیرمنتظره افتاد!!
اصطلاح واحد محصولتقویم · رویداد · وظیفه · موعدتققیم · قرار ملاقات (برای رویداد) · ددلاین
ارقام فارسی همه‌جا۷ شهریور · ۰۹:۳۰7 شهریور · 09:30
فعل دوم‌شخص مستقیمرویداد حذف شد — بازگردانیعملیات حذف با موفقیت انجام گرفت