From 937c0090d53117e074c0df2d18fe50185e759029 Mon Sep 17 00:00:00 2001 From: "DESKTOP-PUHFO60\\dsx2016" Date: Mon, 19 Oct 2026 22:10:05 +0800 Subject: [PATCH] Show on-device HTML UI mocks as firmware card previews. Prefer media/preview.html over raster covers so catalog cards mirror each LVGL screen. Co-authored-by: Cursor --- README.md | 13 +++---- components/firmware-card.tsx | 60 +++++---------------------------- components/firmware-detail.tsx | 19 ++++------- components/firmware-preview.tsx | 52 ++++++++++++++++++++++++++++ components/ui-preview.tsx | 27 +++++++++++++++ lib/firmware.ts | 6 ++++ messages/en.json | 2 +- messages/zh.json | 2 +- 8 files changed, 108 insertions(+), 73 deletions(-) create mode 100644 components/firmware-preview.tsx create mode 100644 components/ui-preview.tsx diff --git a/README.md b/README.md index 849022f..e3962d3 100644 --- a/README.md +++ b/README.md @@ -47,9 +47,11 @@ CYD_FIRMWARE_ROOT=C:\Users\dsx2016\Desktop\codes\cyd After rebuilding a project, run its `firmware\export_from_build.ps1`, then click **Refresh**. -## Extending a firmware (media / docs) +## Extending a firmware (HTML UI preview / docs) -Create `meta.json` beside the `.bin` files: +Preferred card preview: **`media/preview.html`** — HTML recreation of the on-device LVGL UI (320×240). Auto-detected if present. + +Optional `meta.json` beside the `.bin` files: ```json { @@ -59,19 +61,18 @@ Create `meta.json` beside the `.bin` files: "description": "Longer detail text", "tags": ["pomodoro", "touch"], "media": { - "cover": "media/cover.webp", - "animation": "media/preview.gif", + "preview": "media/preview.html", "video": "media/demo.mp4", "docs": "docs/README.md" } } ``` -- Relative media paths are served via `/api/firmware/.../media/...` (only if the file exists). +- Media paths are served via `/api/firmware/.../media/...` (only if the file exists). - `docs` may also be an `https://` URL. - `boardId` values: `esp32-2432s028` (active), `esp32-2432s024`, `esp32-3248s035`, `esp32-s3-touch` (UI reserved). -Without `meta.json`, the catalog still works from `VERSION.txt`. +Without `meta.json`, the catalog still works from `VERSION.txt` + auto `media/preview.html`. ## Public deploy (Docker + Caddy) diff --git a/components/firmware-card.tsx b/components/firmware-card.tsx index 371559e..9e9d848 100644 --- a/components/firmware-card.tsx +++ b/components/firmware-card.tsx @@ -1,48 +1,10 @@ "use client"; -import { Film, FileText, ImageIcon } from "lucide-react"; +import { FileText, LayoutTemplate } from "lucide-react"; import type { FirmwareInfo } from "@/lib/firmware"; import { formatBytes, cn } from "@/lib/utils"; import { Badge } from "@/components/ui/badge"; - -function MediaSlot({ fw, active }: { fw: FirmwareInfo; active: boolean }) { - const src = fw.media.animation || fw.media.cover; - if (src) { - return ( - // Dynamic firmware media URLs — next/image needs remotePatterns per host - // eslint-disable-next-line @next/next/no-img-element -- local API / arbitrary media - - ); - } - - const initials = fw.name - .replace(/[^A-Za-z0-9\u4e00-\u9fff]+/g, " ") - .trim() - .split(/\s+/) - .slice(0, 2) - .map((w) => w[0]?.toUpperCase() ?? "") - .join(""); - - return ( -
- - {initials || "FW"} - - - preview soon - -
- ); -} +import { FirmwarePreview } from "@/components/firmware-preview"; export function FirmwareCard({ fw, @@ -53,9 +15,8 @@ export function FirmwareCard({ active: boolean; onSelect: () => void; }) { - const hasVideo = Boolean(fw.media.video); + const hasPreview = Boolean(fw.media.preview); const hasDocs = Boolean(fw.media.docs); - const hasCover = Boolean(fw.media.cover || fw.media.animation); return (