From 5b6f3e851bd3cb7d00cfa983ad77f16ebfea1f9a Mon Sep 17 00:00:00 2001 From: "soroush.asadi" Date: Wed, 3 Jun 2026 00:51:52 +0330 Subject: [PATCH] feat(admin): full-screen forms + WYSIWYG rich-text editor MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - AdminResource + TemplatesAdmin modals are now large full-height panels (max-w-5xl, sticky header/footer, scrolling body, 2-column field grid; textarea/richtext span full width) - RichTextField: dependency-free contentEditable WYSIWYG (bold/italic/underline, H2/H3/¶, lists, link, clear) emitting HTML, dir="auto" for fa/en - blog content + category description now use the rich editor Co-Authored-By: Claude Opus 4.8 --- src/components/admin/AdminResource.tsx | 28 +++++---- src/components/admin/RichTextField.tsx | 76 ++++++++++++++++++++++++ src/components/admin/TemplatesAdmin.tsx | 13 ++-- src/components/admin/admin-resources.tsx | 4 +- 4 files changed, 103 insertions(+), 18 deletions(-) create mode 100644 src/components/admin/RichTextField.tsx diff --git a/src/components/admin/AdminResource.tsx b/src/components/admin/AdminResource.tsx index e85f2f8..392d9ae 100644 --- a/src/components/admin/AdminResource.tsx +++ b/src/components/admin/AdminResource.tsx @@ -4,11 +4,12 @@ import { useCallback, useEffect, useState, type ReactNode } from "react"; import { FileUploadField } from "@/components/admin/FileUploadField"; import { AdminThumb } from "@/components/admin/AdminThumb"; +import { RichTextField } from "@/components/admin/RichTextField"; export interface FieldDef { key: string; label: string; - type?: "text" | "textarea" | "number" | "checkbox" | "select" | "image" | "file"; + type?: "text" | "textarea" | "richtext" | "number" | "checkbox" | "select" | "image" | "file"; options?: { value: string; label: string }[]; required?: boolean; placeholder?: string; @@ -193,21 +194,26 @@ export function AdminResource({ config }: { config: ResourceConfig }) { {(creating || editing) && config.fields && ( -
-
e.stopPropagation()}> -

- {editing ? "ویرایش" : "افزودن"} — {config.title} -

-
+
+
e.stopPropagation()}> +
+

+ {editing ? "ویرایش" : "افزودن"} — {config.title} +

+ +
+
{config.fields.map((f) => ( -
+
{f.type !== "checkbox" && ( )} - {f.type === "textarea" ? ( -