'use client'

import * as React from 'react'
import * as AvatarPrimitive from '@radix-ui/react-avatar'
import { cva, type VariantProps } from 'class-variance-authority'

import { cn } from '@/lib/utils'

const avatarVariants = cva(
  'relative flex shrink-0 overflow-hidden',
  {
    variants: {
      size: {
        xs: 'size-6 text-[10px]',
        sm: 'size-8 text-xs',
        default: 'size-10 text-sm',
        lg: 'size-12 text-base',
        xl: 'size-16 text-lg',
        '2xl': 'size-24 text-2xl',
      },
      shape: {
        circle: 'rounded-full',
        square: 'rounded-lg',
        hex: '[clip-path:polygon(25%_0%,75%_0%,100%_50%,75%_100%,25%_100%,0%_50%)]',
      },
      ring: {
        none: '',
        default: 'ring-2 ring-border ring-offset-2 ring-offset-background',
        primary: 'ring-2 ring-primary ring-offset-2 ring-offset-background',
        gradient: 'p-0.5 bg-gradient-to-br from-primary to-secondary',
        story: 'p-0.5 bg-gradient-to-br from-primary via-secondary to-primary',
        live: 'p-0.5 bg-secondary animate-pulse',
      },
    },
    defaultVariants: {
      size: 'default',
      shape: 'circle',
      ring: 'none',
    },
  },
)

interface AvatarProps
  extends React.ComponentProps<typeof AvatarPrimitive.Root>,
    VariantProps<typeof avatarVariants> {
  status?: 'online' | 'away' | 'busy' | 'offline'
}

function Avatar({
  className,
  size,
  shape,
  ring,
  status,
  children,
  ...props
}: AvatarProps) {
  const hasRingWithPadding = ring === 'gradient' || ring === 'story' || ring === 'live'
  
  return (
    <div className={cn(avatarVariants({ size, shape, ring }), 'inline-flex')}>
      <AvatarPrimitive.Root
        data-slot="avatar"
        className={cn(
          'relative flex size-full shrink-0 overflow-hidden bg-muted',
          shape === 'circle' && 'rounded-full',
          shape === 'square' && 'rounded-md',
          shape === 'hex' && '[clip-path:polygon(25%_0%,75%_0%,100%_50%,75%_100%,25%_100%,0%_50%)]',
          hasRingWithPadding && 'bg-background',
          className,
        )}
        {...props}
      >
        {children}
      </AvatarPrimitive.Root>
      
      {status && (
        <AvatarStatus status={status} size={size} />
      )}
    </div>
  )
}

function AvatarImage({
  className,
  ...props
}: React.ComponentProps<typeof AvatarPrimitive.Image>) {
  return (
    <AvatarPrimitive.Image
      data-slot="avatar-image"
      className={cn('aspect-square size-full object-cover', className)}
      {...props}
    />
  )
}

function AvatarFallback({
  className,
  ...props
}: React.ComponentProps<typeof AvatarPrimitive.Fallback>) {
  return (
    <AvatarPrimitive.Fallback
      data-slot="avatar-fallback"
      className={cn(
        'flex size-full items-center justify-center bg-gradient-to-br from-primary to-secondary font-semibold text-primary-foreground',
        className,
      )}
      {...props}
    />
  )
}

interface AvatarStatusProps {
  status: 'online' | 'away' | 'busy' | 'offline'
  size?: VariantProps<typeof avatarVariants>['size']
}

function AvatarStatus({ status, size }: AvatarStatusProps) {
  const statusStyles = {
    online: 'bg-success shadow-[0_0_8px_oklch(0.72_0.19_145_/_0.6)]',
    away: 'bg-warning',
    busy: 'bg-destructive',
    offline: 'bg-muted-foreground',
  }
  
  const sizeStyles = {
    xs: 'size-1.5 border',
    sm: 'size-2 border',
    default: 'size-2.5 border-2',
    lg: 'size-3 border-2',
    xl: 'size-4 border-2',
    '2xl': 'size-5 border-[3px]',
  }

  return (
    <span
      data-slot="avatar-status"
      className={cn(
        'absolute bottom-0 right-0 rounded-full border-background',
        statusStyles[status],
        sizeStyles[size || 'default'],
      )}
    />
  )
}

// Avatar Group for stacked avatars
interface AvatarGroupProps extends React.ComponentProps<'div'> {
  max?: number
  size?: VariantProps<typeof avatarVariants>['size']
}

function AvatarGroup({
  className,
  children,
  max = 4,
  size = 'default',
  ...props
}: AvatarGroupProps) {
  const childArray = React.Children.toArray(children)
  const visibleChildren = childArray.slice(0, max)
  const remainingCount = childArray.length - max

  return (
    <div
      data-slot="avatar-group"
      className={cn('flex -space-x-2', className)}
      {...props}
    >
      {visibleChildren.map((child, index) => (
        <div key={index} className="relative" style={{ zIndex: visibleChildren.length - index }}>
          {React.isValidElement(child)
            ? React.cloneElement(child as React.ReactElement<AvatarProps>, { size, ring: 'default' })
            : child
          }
        </div>
      ))}
      {remainingCount > 0 && (
        <Avatar size={size} ring="default">
          <AvatarFallback className="bg-muted text-muted-foreground text-xs font-medium">
            +{remainingCount}
          </AvatarFallback>
        </Avatar>
      )}
    </div>
  )
}

export { Avatar, AvatarImage, AvatarFallback, AvatarStatus, AvatarGroup, avatarVariants }
