تنظیمِ اعلانها
پیشنمایش تمامصفحهتنظیمِ اعلانها به شکلِ جدولِ رویداد × کانال (ایمیل، پیامک، اپ) با چکباکس، گروهبندیِ رویدادها و «همه را خاموش کن».
۱. نصب کامپوننتها
این بلاک از ۵ آیتم دیگ استفاده میکند: buttoncheckboxcontrol-sizetabletoast
پکیجمنیجر پیشفرض Node.jsنصب سریع با لینک سخت و دیسک مشترکYarn نسخهٔ ۲ به بالا (Berry)رانتایم و پکیجمنیجر Bun
npx digdesign@latest add https://docs.digdesign.ir/r/button.json https://docs.digdesign.ir/r/checkbox.json https://docs.digdesign.ir/r/control-size.json https://docs.digdesign.ir/r/table.json https://docs.digdesign.ir/r/toast.jsonpnpm dlx digdesign@latest add https://docs.digdesign.ir/r/button.json https://docs.digdesign.ir/r/checkbox.json https://docs.digdesign.ir/r/control-size.json https://docs.digdesign.ir/r/table.json https://docs.digdesign.ir/r/toast.jsonyarn dlx digdesign@latest add https://docs.digdesign.ir/r/button.json https://docs.digdesign.ir/r/checkbox.json https://docs.digdesign.ir/r/control-size.json https://docs.digdesign.ir/r/table.json https://docs.digdesign.ir/r/toast.jsonbunx --bun digdesign@latest add https://docs.digdesign.ir/r/button.json https://docs.digdesign.ir/r/checkbox.json https://docs.digdesign.ir/r/control-size.json https://docs.digdesign.ir/r/table.json https://docs.digdesign.ir/r/toast.json۲. کد صفحه
کد را در app/<route>/page.tsx بگذارید و متنها، داده و هندلرها را با محصول خودتان عوض کنید.
settings-notifications.tsx
"use client"
import * as React from "react"
import { Button } from "@/components/ui/button"
import { Checkbox } from "@/components/ui/checkbox"
import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table"
import { ControlSizeProvider } from "@/components/ui/control-size"
import { toast } from "@/components/ui/toast"
const CHANNELS = ["ایمیل", "پیامک", "اپ"] as const
const EVENTS = [
{ group: "سفارشها", items: ["سفارشِ تازه", "تغییرِ وضعیتِ ارسال", "مرجوعی"] },
{ group: "مالی", items: ["پرداختِ موفق", "سررسیدِ فاکتور"] },
{ group: "تیم", items: ["دعوتِ عضوِ تازه", "نامبردن از من"] },
]
/**
* تنظیمِ اعلانها به شکلِ جدولِ رویداد × کانال: هر ردیف یک رویداد، هر ستون یک کانال (ایمیل،
* پیامک، اپ) با چکباکس؛ تیترِ هر گروه جدا و «همه را خاموش کن» برای وقتِ مرخصی.
*/
export default function SettingsNotificationsBlock() {
const [on, setOn] = React.useState<Record<string, boolean>>(() =>
Object.fromEntries(EVENTS.flatMap((group) => group.items.flatMap((item) => CHANNELS.map((channel) => [`${item}:${channel}`, channel !== "پیامک" || item.includes("پرداخت")]))))
)
const toggle = (key: string) => setOn((state) => ({ ...state, [key]: !state[key] }))
return (
<ControlSizeProvider size="xl" asChild>
<main className="mx-auto flex w-full max-w-3xl flex-col gap-8 p-4 sm:p-6">
<header className="flex flex-wrap items-end justify-between gap-x-4 gap-y-6">
<div className="flex flex-col gap-1">
<h1 className="text-2xl font-bold">اعلانها</h1>
<p className="text-muted-foreground">برای هر رویداد انتخاب کن از کجا خبردار شوی.</p>
</div>
<Button variant="outline" onClick={() => setOn((state) => Object.fromEntries(Object.keys(state).map((key) => [key, false])))}>
همه را خاموش کن
</Button>
</header>
<div className="rounded-xl border border-border bg-card">
<Table stackOnMobile className="min-w-[30rem]">
<TableHeader className="bg-subtle">
<TableRow className="hover:bg-subtle">
<TableHead>رویداد</TableHead>
{CHANNELS.map((channel) => (
<TableHead key={channel} className="w-24 text-center">
{channel}
</TableHead>
))}
</TableRow>
</TableHeader>
<TableBody>
{EVENTS.map((group) => (
<React.Fragment key={group.group}>
<TableRow className="hover:bg-card">
<TableCell colSpan={CHANNELS.length + 1} className="pt-5 pb-2 font-bold">
{group.group}
</TableCell>
</TableRow>
{group.items.map((item) => (
<TableRow key={item}>
<TableCell>{item}</TableCell>
{CHANNELS.map((channel) => {
const key = `${item}:${channel}`
return (
<TableCell key={channel} className="text-center">
<Checkbox checked={on[key]} onCheckedChange={() => toggle(key)} aria-label={`${item} از ${channel}`} />
</TableCell>
)
})}
</TableRow>
))}
</React.Fragment>
))}
</TableBody>
</Table>
</div>
<div className="flex justify-end border-t border-border pt-8">
<Button onClick={() => toast.success("تنظیمِ اعلانها ذخیره شد.")}>ذخیره</Button>
</div>
</main>
</ControlSizeProvider>
)
}