Files
www_mycelium_cloud2/src/components/ui/Button.tsx
2025-09-15 16:51:05 +02:00

60 lines
2.0 KiB
TypeScript

import Link from 'next/link'
import clsx from 'clsx'
const baseStyles = {
solid:
'inline-flex justify-center rounded-lg py-2 px-3 text-sm font-semibold transition-colors',
outline:
'inline-flex justify-center rounded-lg border py-[calc(theme(spacing.2)-1px)] px-[calc(theme(spacing.3)-1px)] text-sm transition-colors',
}
const variantStyles = {
solid: {
primary: 'bg-[#005eff] text-white hover:bg-[#005eff]/90 active:bg-[#005eff]/80',
white: 'bg-white text-black hover:bg-white/90 active:bg-white/90 active:text-gray-400',
gray: 'bg-gray-800 text-white hover:bg-gray-900 active:bg-gray-800 active:text-white/80',
},
outline: {
primary: 'border-[#005eff] text-[#005eff] hover:border-[#005eff]/80 hover:text-[#005eff]/80 active:bg-gray-100 active:text-[#005eff]/70',
gray: 'border-gray-300 text-gray-700 hover:border-gray-400 active:bg-gray-100 active:text-gray-700/80',
},
}
type ButtonProps = (
| { variant?: 'solid'; color?: keyof typeof variantStyles.solid }
| { variant: 'outline'; color?: keyof typeof variantStyles.outline }
) & (
| Omit<React.ComponentPropsWithoutRef<typeof Link>, 'color'>
| (Omit<React.ComponentPropsWithoutRef<'button'>, 'color'> & {
href?: undefined
})
)
export function Button({ className, ...props }: ButtonProps) {
props.variant ??= 'solid'
if (props.variant === 'solid') {
props.color ??= 'primary'
} else {
props.color ??= 'gray'
}
let variantClass: string | undefined;
if (props.variant === 'outline') {
variantClass = variantStyles.outline[props.color as keyof typeof variantStyles.outline];
} else if (props.variant === 'solid') {
variantClass = variantStyles.solid[props.color as keyof typeof variantStyles.solid];
}
className = clsx(
baseStyles[props.variant],
variantClass,
className,
)
return typeof props.href === 'undefined' ? (
<button className={className} {...props} />
) : (
<Link className={className} {...props} />
)
}