feat(frontend): slice 2 — migrate 11 shared components to shadcn/Tailwind

Web UI rework. Shared-components slice (drift prevention):
- Migrate SectionCard, SelectionRailCard, TabbedCard, MetricCard,
  DiskSpaceCard, HoverEditButton, DialogFooter, ConfirmDialog,
  LibraryOverview, NowPlaying, SessionActivityPanel off @mui
- HoverEditButton: MUI IconButton + EditOutlined -> Button + lucide Pencil
- Status mapping uses the success Badge variant (chart-2) for healthy
- Exported APIs preserved so consuming pages still compile (no page edits)
- 11 behavioral Vitest component tests added

Gate: build + lint + test green.
This commit is contained in:
Developer
2026-06-17 12:33:47 +00:00
parent dd778d8850
commit 109e74db41
23 changed files with 830 additions and 469 deletions
+17 -12
View File
@@ -1,32 +1,37 @@
import EditOutlinedIcon from "@mui/icons-material/EditOutlined";
import { IconButton } from "@mui/material";
import { Pencil } from "lucide-react";
import { Button } from "@/components/ui/button";
interface HoverEditButtonProps {
onClick: () => void;
label?: string;
}
/**
* Hover-to-reveal edit affordance.
*
* Keeps the `rail-edit` class plus the opacity-0 base + transition so the
* existing hover-reveal rules in consuming pages (Actions, Settings) still
* target it (`&:hover .rail-edit { opacity: 1 }`) until those pages migrate.
* MUI IconButton + EditOutlined → shadcn `Button variant="ghost" size="icon-sm"`
* + lucide `Pencil`. Same exported props/display name.
*/
export function HoverEditButton({
onClick,
label = "Edit",
}: HoverEditButtonProps) {
return (
<IconButton
className="rail-edit"
<Button
variant="ghost"
size="icon-sm"
className="rail-edit text-muted-foreground opacity-0 transition-opacity duration-100 ease-out"
aria-label={label}
size="small"
onMouseDown={(e) => e.stopPropagation()}
onClick={(e) => {
e.stopPropagation();
onClick();
}}
sx={{
opacity: 0,
transition: "opacity 120ms ease",
color: "text.secondary",
}}
>
<EditOutlinedIcon fontSize="inherit" />
</IconButton>
<Pencil />
</Button>
);
}