Make /admin/catalog a full-screen catalog studio that replaces the old listing plus separate [id]/builder-club detail pages: - Embed CatalogManagerWorkspace on /admin/catalog with a Normal/Builder Club toggle, Catalog Sync status, packages (normal), Organize imports and a diagnostics link to /admin/studio/maintenance. - Manage BC items directly in the studio Items tab (new BcItemsEditor, CRUD via existing bc actions; /api/admin/catalog/items now serves BC). - Inline editor: add pageTextTeaser field for both catalogs and remove the legacy full-editor links. - Remove the 'Open full editor' context action from the tree. - Move catalog-items-table (dir + barrel) and catalog-translate-tab out of the app route into src/components/admin/catalog and update all importers. - Keep /admin/catalog/[id], builder-club/[id] and /admin/catalog/maintenance as redirects into the new studio; consolidate maintenance panels into /admin/studio/maintenance and point the nav item there. - Delete the old listing/table/tabs/forms and the standalone bc-manager.
68 lines
1.8 KiB
TypeScript
68 lines
1.8 KiB
TypeScript
"use client";
|
|
|
|
import { Package } from "lucide-react";
|
|
import type { CatalogItemData } from "@/components/admin/catalog/catalog-items-table/types";
|
|
import { cn } from "@/lib/utils";
|
|
import {
|
|
getShopGridClass,
|
|
getShopTileSize,
|
|
parseFirstItemId,
|
|
ShopTile,
|
|
} from "./shop-tile";
|
|
|
|
interface ItemsShopPreviewProps {
|
|
items: CatalogItemData[];
|
|
furniRevisionMap: Record<number, { classname: string; revision: number }>;
|
|
layout: string;
|
|
canEdit: boolean;
|
|
onItemClick?: (item: CatalogItemData) => void;
|
|
}
|
|
|
|
export function ItemsShopPreview({
|
|
items,
|
|
furniRevisionMap,
|
|
layout,
|
|
canEdit,
|
|
onItemClick,
|
|
}: ItemsShopPreviewProps) {
|
|
if (items.length === 0) {
|
|
return (
|
|
<div className="flex flex-col items-center justify-center rounded-lg border-2 border-dashed p-12 text-center">
|
|
<Package className="h-10 w-10 text-muted-foreground/40" />
|
|
<p className="mt-2 text-sm text-muted-foreground">
|
|
No items in this page yet
|
|
</p>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
const gridClass = getShopGridClass(layout);
|
|
const tileSize = getShopTileSize(layout);
|
|
|
|
return (
|
|
<div className="rounded-lg border bg-gradient-to-b from-[var(--admin-surface)] to-[var(--admin-canvas)] p-4">
|
|
<div className="mb-3 flex items-center justify-between text-xs text-[var(--admin-text-muted)]">
|
|
<span className="font-medium">Shop preview · {layout}</span>
|
|
<span>{items.length} items</span>
|
|
</div>
|
|
<div className={cn("grid gap-2", gridClass)}>
|
|
{items.map((item) => {
|
|
const firstId = parseFirstItemId(item.itemIds);
|
|
const furni = firstId != null ? furniRevisionMap[firstId] : undefined;
|
|
|
|
return (
|
|
<ShopTile
|
|
key={item.id}
|
|
item={item}
|
|
furni={furni}
|
|
iconHeight={tileSize}
|
|
canEdit={canEdit}
|
|
onClick={onItemClick}
|
|
/>
|
|
);
|
|
})}
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|