Uecko_ERP/apps/web/src/layout/app-company-switcher.tsx
2026-07-06 17:33:45 +02:00

104 lines
3.7 KiB
TypeScript

import {
DropdownMenu,
DropdownMenuContent,
DropdownMenuGroup,
DropdownMenuItem,
DropdownMenuLabel,
DropdownMenuSeparator,
DropdownMenuTrigger,
} from "@repo/shadcn-ui/components";
import { cn } from "@repo/shadcn-ui/lib/utils";
import { CheckIcon, ChevronDownIcon } from "lucide-react";
import { useAppCompanySwitcherController } from "../lib/hooks";
interface AppCompanySwitcherProps {
className?: string;
}
export const AppCompanySwitcher = ({ className }: AppCompanySwitcherProps) => {
const { activeCompany, companies, handleSelectCompany, isChangingCompany, isDisabled } =
useAppCompanySwitcherController();
if (!activeCompany) {
return null;
}
return (
<div className={cn("w-full", className)}>
<DropdownMenu>
<DropdownMenuTrigger
render={
<button
aria-busy={isChangingCompany}
aria-label="Switch active company"
className={cn(
"flex h-14 w-full items-center gap-3 rounded-none px-3 text-left hover:bg-muted transition-colors",
isChangingCompany && "cursor-wait opacity-80",
"focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring"
)}
disabled={isDisabled}
type="button"
>
<span className="flex h-9 w-9 shrink-0 items-center justify-center rounded-lg bg-blue-600 text-sm font-semibold text-white">
{activeCompany.initials}
</span>
<span className="min-w-0 flex-1 group-data-[collapsible=icon]:hidden">
<span className="block truncate text-sm font-semibold leading-5 text-foreground">
{activeCompany.name}
</span>
{activeCompany.secondaryLabel ? (
<span className="block truncate text-xs text-muted-foreground">
{activeCompany.secondaryLabel}
</span>
) : null}
</span>
<ChevronDownIcon
aria-hidden="true"
className="size-4 shrink-0 text-muted-foreground group-data-[collapsible=icon]:hidden"
/>
</button>
}
/>
<DropdownMenuContent align="start" className="w-64" side="bottom">
<DropdownMenuGroup>
<DropdownMenuLabel>Empresa activa</DropdownMenuLabel>
<DropdownMenuSeparator />
{companies.map((company) => {
return (
<DropdownMenuItem
className="gap-3 py-2"
disabled={company.isSelected || isChangingCompany}
key={company.id}
onSelect={() => handleSelectCompany(company.id)}
>
<span className="flex h-8 w-8 shrink-0 items-center justify-center rounded-md bg-muted text-xs font-semibold text-foreground">
{company.initials}
</span>
<span className="min-w-0 flex-1">
<span className="block truncate font-medium">{company.name}</span>
{company.secondaryLabel ? (
<span className="block truncate text-xs text-muted-foreground">
{company.secondaryLabel}
</span>
) : null}
</span>
{company.isSelected ? (
<CheckIcon aria-hidden="true" className="size-4 text-blue-600" />
) : null}
</DropdownMenuItem>
);
})}
</DropdownMenuGroup>
</DropdownMenuContent>
</DropdownMenu>
</div>
);
};