import Link from "next/link";
import { AnchorHTMLAttributes, ButtonHTMLAttributes } from "react";

type ButtonVariant = "primary" | "secondary" | "outline" | "ghost";

interface BaseButtonProps {
  variant?: ButtonVariant;
  fullWidth?: boolean;
  showArrow?: boolean;
  children: React.ReactNode;
  className?: string;
}

interface LinkButtonProps extends BaseButtonProps {
  href: string;
  external?: boolean;
}

interface ActionButtonProps extends BaseButtonProps {
  onClick?: () => void;
  type?: "button" | "submit" | "reset";
  disabled?: boolean;
}

type ButtonProps = LinkButtonProps | ActionButtonProps;

const baseStyles =
  "inline-block font-semibold transition-all duration-200 text-center text-base";

const variantStyles: Record<ButtonVariant, string> = {
  primary:
    "bg-primary hover:bg-primary-dark text-white shadow-lg hover:shadow-xl",
  secondary:
    "bg-secondary hover:bg-secondary-dark text-white shadow-lg hover:shadow-xl",
  outline:
    "bg-white border-2 border-primary text-primary hover:bg-primary hover:text-white",
  ghost: "bg-transparent text-primary hover:bg-primary hover:bg-opacity-10",
};

const variantStylesWithArrow: Record<ButtonVariant, string> = {
  primary: "bg-primary hover:bg-black text-white shadow-lg hover:shadow-xl",
  secondary: "bg-secondary hover:bg-black text-white shadow-lg hover:shadow-xl",
  outline:
    "bg-transparent border-2 border-primary text-primary hover:bg-black hover:text-white",
  ghost: "bg-transparent text-primary hover:bg-black hover:bg-opacity-10",
};

function isLinkButton(props: ButtonProps): props is LinkButtonProps {
  return "href" in props;
}

export default function Button(props: ButtonProps) {
  const {
    variant = "secondary",
    fullWidth = false,
    showArrow = false,
    children,
    className = "",
  } = props;

  const combinedClassName = `
    ${baseStyles}
    ${showArrow ? variantStylesWithArrow[variant] : variantStyles[variant]}
    ${showArrow ? "" : "px-6 py-3"}
    ${fullWidth ? "w-full block" : ""}
    ${className}
  `
    .trim()
    .replace(/\s+/g, " ");

  const arrowHoverColor =
    variant === "primary"
      ? "group-hover:bg-primary"
      : variant === "secondary"
        ? "group-hover:bg-secondary"
        : "group-hover:bg-primary";

  const content = showArrow ? (
    <span className="relative flex items-center overflow-hidden">
      <span className="relative px-6 pr-3 py-3.5">{children}</span>
      <span
        className={`absolute right-0 top-0 bottom-0 w-16 bg-black flex items-center justify-center transition-all duration-300 ${arrowHoverColor}`}
        style={{ clipPath: "polygon(29% 0, 100% 0, 100% 100%, 0% 100%)" }}>
        <svg
          className="w-7 h-7 text-white ml-2 transition-transform duration-300 group-hover:scale-125"
          fill="none"
          stroke="currentColor"
          viewBox="0 0 24 24"
          aria-hidden="true">
          <path
            strokeLinecap="round"
            strokeLinejoin="round"
            strokeWidth={2}
            d="M13 7l5 5m0 0l-5 5m5-5H6"
          />
        </svg>
      </span>
      <span className="w-16 opacity-0" aria-hidden="true"></span>
    </span>
  ) : (
    <>{children}</>
  );

  if (isLinkButton(props)) {
    const { href, external } = props;

    if (external) {
      return (
        <a
          href={href}
          target="_blank"
          rel="noopener noreferrer"
          className={`${combinedClassName} group`}>
          {content}
        </a>
      );
    }

    return (
      <Link href={href} className={`${combinedClassName} group`}>
        {content}
      </Link>
    );
  }

  const { onClick, type = "button", disabled } = props;

  return (
    <button
      type={type}
      onClick={onClick}
      disabled={disabled}
      className={`${combinedClassName} group ${disabled ? "opacity-50 cursor-not-allowed" : ""}`}>
      {content}
    </button>
  );
}
