feat(admin): fix the tab bar on Users + Configuration pages
Apply the fixed-chrome pattern to the two admin pages with a horizontal tab bar: the tabs (and Config's intro) pin in the shell's fixed band while the tab content scrolls under them. Config's floating save bar is unaffected. Suite 15/15, tsc + knip clean.
This commit is contained in:
@@ -9,6 +9,7 @@ import Tooltip from "./Tooltip";
|
||||
import { Section } from "./ui/form";
|
||||
import { useConfirm } from "./ConfirmProvider";
|
||||
import Tabs, { usePersistedTab } from "./Tabs";
|
||||
import { PageToolbar } from "./PageShell";
|
||||
|
||||
// Admin-only user & access management: roles, access requests (the Invite whitelist), and the
|
||||
// demo whitelist + reset. Each section is its own tab (persisted across reloads); the Access tab
|
||||
@@ -26,12 +27,19 @@ export default function AdminUsers({ me }: { me: Me }) {
|
||||
];
|
||||
const active = tabs.some((x) => x.id === tab) ? tab : "roles";
|
||||
return (
|
||||
<div className="p-4 max-w-3xl w-full mx-auto">
|
||||
<Tabs tabs={tabs} active={active} onChange={setTab} />
|
||||
{active === "roles" && <UsersRoles me={me} />}
|
||||
{active === "access" && <AdminInvites />}
|
||||
{active === "demo" && <AdminDemo />}
|
||||
</div>
|
||||
<>
|
||||
{/* The tab bar is fixed chrome; the tab content scrolls under it. */}
|
||||
<PageToolbar>
|
||||
<div className="px-4 pt-3 max-w-3xl w-full mx-auto">
|
||||
<Tabs tabs={tabs} active={active} onChange={setTab} />
|
||||
</div>
|
||||
</PageToolbar>
|
||||
<div className="px-4 pb-4 pt-3 max-w-3xl w-full mx-auto">
|
||||
{active === "roles" && <UsersRoles me={me} />}
|
||||
{active === "access" && <AdminInvites />}
|
||||
{active === "demo" && <AdminDemo />}
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
@@ -6,6 +6,7 @@ import { api, type ConfigItem, type PlexTestResult } from "../lib/api";
|
||||
import { notify } from "../lib/notifications";
|
||||
import Tooltip from "./Tooltip";
|
||||
import Tabs, { usePersistedTab } from "./Tabs";
|
||||
import { PageToolbar } from "./PageShell";
|
||||
import { Switch } from "./ui/form";
|
||||
import { DraftSaveBar, type SaveState } from "./ui/DraftSaveBar";
|
||||
import { LS } from "../lib/storage";
|
||||
@@ -151,11 +152,15 @@ export default function ConfigPanel() {
|
||||
}));
|
||||
|
||||
return (
|
||||
<div className="p-4 max-w-3xl w-full mx-auto pb-24">
|
||||
<p className="text-xs text-muted mb-4 leading-relaxed">{t("config.intro")}</p>
|
||||
|
||||
<Tabs tabs={groupTabs} active={activeGroup} onChange={setTab} />
|
||||
|
||||
<>
|
||||
{/* Intro + tab bar are fixed chrome; the config fields scroll under them. */}
|
||||
<PageToolbar>
|
||||
<div className="px-4 pt-3 max-w-3xl w-full mx-auto">
|
||||
<p className="text-xs text-muted mb-3 leading-relaxed">{t("config.intro")}</p>
|
||||
<Tabs tabs={groupTabs} active={activeGroup} onChange={setTab} />
|
||||
</div>
|
||||
</PageToolbar>
|
||||
<div className="px-4 pb-24 pt-3 max-w-3xl w-full mx-auto">
|
||||
{activeGroup && (
|
||||
<div className="glass rounded-2xl p-4 mb-4">
|
||||
<div className="divide-y divide-border/60">
|
||||
@@ -264,6 +269,7 @@ export default function ConfigPanel() {
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user