تخطَّ إلى المحتوى

Dialog

نافذة فوق الصفحة لقرار أو مهمة قصيرة. ثلاثة عروض وزر إغلاق، ويُحبس التركيز فيها ثم يعود إلى الزر.

الإصدار 0.4.1 ·

نافذة حوار

التثبيت

bunx --bun shadcn@latest add @dga/dialog

الاستخدام

page.tsx
tsx
import { Button } from "@/components/ui/button";
import {
  Dialog,
  DialogClose,
  DialogContent,
  DialogDescription,
  DialogFooter,
  DialogHeader,
  DialogTitle,
  DialogTrigger,
} from "@/components/ui/dialog";

export function CancelRequest() {
  return (
    <Dialog>
      <DialogTrigger render={<Button variant="outline" />}>إلغاء الطلب</DialogTrigger>
      <DialogContent closeLabel="إغلاق">
        <DialogHeader>
          <DialogTitle>إلغاء هذا الطلب؟</DialogTitle>
          <DialogDescription>سيُسحب الطلب ٢٤٨١٠. يمكنك تقديمه مرة أخرى لاحقًا.</DialogDescription>
        </DialogHeader>
        <DialogFooter>
          <DialogClose render={<Button variant="outline" />}>الإبقاء على الطلب</DialogClose>
          <DialogClose render={<Button destructive />}>إلغاء الطلب</DialogClose>
        </DialogFooter>
      </DialogContent>
    </Dialog>
  );
}

استخدم Dialog حين يجب على الشخص أن يجيب أو ينهي أمرًا قبل المتابعة: تأكيد إجراء مدمّر أو تعديل بضعة حقول أو قراءة شروط. ولا تستخدمه لرسالة لا تحتاج إجابة (استخدم Toast أو Inline Alert) ولا لصفحة طويلة من المحتوى. أعطه دائمًا DialogTitle، فهو يسمّي النافذة لقارئ الشاشة. وضع الإجراء الرئيس أخيرًا، وسمِّ الإجراءات بما تفعله («إلغاء الطلب») لا «نعم» و«لا». وcloseLabel هو الاسم الذي يقرؤه قارئ الشاشة لزر الإغلاق؛ ترجمه في الصفحات العربية.

البنية

  • الخلفية: تعتّم الصفحة وتعطّلها.
  • المحتوى (role="dialog"): البطاقة. عرضها 600px افتراضيًا، وارتفاعها بقدر الشاشة على الأكثر، وتُمرَّر من الداخل.
  • الترويسة: DialogTitle وDialogDescription.
  • الجسم (اختياري): DialogBody للحقول أو النص.
  • التذييل: الإجراءات، محاذاة إلى النهاية. ويغلق DialogClose النافذة.
  • زر الإغلاق: في الزاوية، في جهة النهاية.

أمثلة

الأحجام

قيمة size إما sm (‏400px) أو md (‏600px، عرض DGA) أو lg (‏800px). وكلها تتقلص لتناسب الجوال.

الأحجام

مع نموذج

ضع الحقول في DialogBody. وتُمرَّر النافذة إن زاد طولها على الشاشة. ويُسمّى Field داخلها ويُربط كالمعتاد.

مع نموذج

يجب الرد عليه

اضبط disablePointerDismissal على Dialog لقرار لا يمكن تخطيه: لا يغلق النقر خارج النافذة النافذةَ بعد الآن، ويظل Escape يغلقها. اقرنه بـ showCloseButton={false} فلا يبقى للخروج إلا الإجراءات في التذييل.

يجب الرد عليه

مُدار

مرّر open وonOpenChange لتملك الحالة: افتح النافذة من شيفرتك، وأغلقها حين ينتهي الطلب. الزر المشغّل اختياري.

مُدار

RTL

ينتقل زر الإغلاق إلى اليسار، وتُحاذى إجراءات التذييل إلى اليسار، وتظهر النافذة بالتلاشي والتكبير نفسه. ولا شيء يُعكس يدويًا: فالتخطيط يستخدم start وend.

LTR (الإنجليزية)
RTL (العربية)

إمكانية الوصول

المفتاحالإجراء
Tabينقل التركيز إلى العنصر التالي داخل النافذة. وعند الأخير يعود إلى الأول: فلا يغادر التركيز النافذة.
Shift + Tabيعيد التركيز إلى الخلف.
Escapeيغلق النافذة ويعيد التركيز إلى العنصر الذي فتحها.
Enterيضغط الزر المركَّز.
  • مبنية على Base UI Dialog: role="dialog" وaria-modal وaria-labelledby ‏(DialogTitle) وaria-describedby ‏(DialogDescription).
  • ينتقل التركيز إلى النافذة عند فتحها ويُحبس فيها ويعود إلى الزر عند إغلاقها. والصفحة خلفها معطّلة وتمريرها مقفل.
  • اضبط disablePointerDismissal على Dialog لقرار لا بد من الإجابة عنه، فلا يغلقها النقر خارجها. ويبقى Escape يغلقها.
  • لزر الإغلاق اسم (closeLabel). والعناوين والنصوص بنسبة 4.5:1 والأيقونات 3:1 أو أفضل، فاتحًا وداكنًا.
  • تظهر النافذة بالتلاشي والتكبير؛ ومع تقليل الحركة تظهر دون حركة.

مرجع API

Dialog

نافذة فوق الصفحة لقرار أو مهمة قصيرة (في DGA: Modal). يدخل التركيز إليها ويبقى فيها، والصفحة خلفها معطّلة، ويغلقها Escape، ويعود التركيز إلى الزر الذي فتحها.

خصائص Dialog
الخاصيةالنوعالقيمة الافتراضية
boolean

مفتوحة في البداية (دون تحكم).

لا توجد قيمة افتراضية
boolean

يمنع الإغلاق بالنقر خارجها. استخدمه لقرار لا بد من الإجابة عنه؛ ويبقى Escape والأزرار تغلقها.

لا توجد قيمة افتراضية
boolean | "trap-focus"

القيمة `true` (الافتراضية) تعطّل الصفحة خلفها وتقفل تمريرها.

لا توجد قيمة افتراضية
(open: boolean) => void

تُستدعى عند فتحها أو إغلاقها.

لا توجد قيمة افتراضية
boolean

حالة الفتح بتحكّم خارجي.

لا توجد قيمة افتراضية

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

DialogBody

الجزء الأوسط القابل للتمرير في نافذة طويلة.

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

DialogClose

يغلق النافذة. اعرض Button معه: `<DialogClose render={<Button />}>`.

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

DialogContent

النافذة: خلفية معتمة والبطاقة. في المنتصف، وتُمرَّر إن زاد طولها.

خصائص DialogContent
الخاصيةالنوعالقيمة الافتراضية
"sm" | "md" | "lg"

العرض: `sm` ‏400px، و`md` ‏600px (كما في DGA)، و`lg` ‏800px. وكلها تتقلص لتناسب الجوال.

"md"
boolean

يعرض زر الإغلاق في الزاوية. أوقفه إن كان للتذييل زر خاص به.

true
string

الاسم الذي يقرؤه قارئ الشاشة لزر الإغلاق. ترجمه في الصفحات العربية.

"Close"

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

DialogDescription

يشرح النافذة. مرتبط بها عبر `aria-describedby`.

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

DialogFooter

الإجراءات، محاذاة إلى النهاية. ضع الإجراء الرئيس أخيرًا.

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

DialogHeader

يجمع العنوان والوصف في أعلى النافذة.

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

DialogTitle

اسم النافذة. يقرؤه قارئ الشاشة عند فتحها.

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

DialogTrigger

الزر الذي يفتح النافذة.

يقبل أيضًا جميع خصائص Base UI Dialog (يفتح في نافذة جديدة).

الاختلافات عن DGA

  • يرسم ملف Figma بطاقة بعرض 600px فقط. وأُضيف زر الإغلاق وحبس التركيز ومفتاح Escape وعرضا sm وlg.
  • الخلفية alpha-black-50. وعلى الجوال عرض البطاقة 100% مطروحًا منه 16px من حشوة الصفحة.
التغييرالسبب
Dialog: name, close and focusA window that takes over the page must be operable by keyboard and announced (WAI-ARIA dialog pattern, WCAG 2.1.1, 2.4.3). Built on Base UI Dialog.

عرض جميع الاختلافات (1) لهذا المكوّن أسباب الاختلافات مكتوبة بالإنجليزية.

التباين

14 زوجًا لونيًا فُحص · جميعها تجتاز WCAG 2.1 AAعرض 7 حالة
النمط / الحالةالفاتحالداكن
title14.53:1 AAA15.87:1 AAA
description10.17:1 AAA12.04:1 AAA
body text18.09:1 AAA15.87:1 AAA
close icon18.09:1 3:115.87:1 3:1
close icon, hovered16.44:1 3:19.59:1 3:1
close icon, pressed14.61:1 3:16.95:1 3:1
focus ring18.09:1 3:117.49:1 3:1

يحتاج النص إلى تباين 4.5:1، والأيقونات وحلقات التركيز إلى 3:1. الحالات المعطّلة مستثناة. تقرير التباين الكامل