import { Check, Copy } from "lucide-react";
import { useEffect, useState } from "react";

interface CopyableValueProps {
  className?: string;
  displayValue?: string;
  label: string;
  value: string;
}

interface TooltipPosition {
  left: number;
  top: number;
}

export function CopyableValue({ className, displayValue, label, value }: CopyableValueProps) {
  const [copyState, setCopyState] = useState<"idle" | "copied" | "failed">("idle");
  const [tooltipPosition, setTooltipPosition] = useState<TooltipPosition | null>(null);

  useEffect(() => {
    if (copyState === "idle") {
      return;
    }
    const timeout = window.setTimeout(() => setCopyState("idle"), 1600);
    return () => window.clearTimeout(timeout);
  }, [copyState]);

  const showTooltip = (target: HTMLElement) => {
    const rect = target.getBoundingClientRect();
    setTooltipPosition({
      left: Math.min(window.innerWidth - 24, Math.max(24, rect.left + rect.width / 2)),
      top: rect.top > 90 ? rect.top - 10 : rect.bottom + 10
    });
  };

  const copy = async () => {
    try {
      await copyText(value);
      setCopyState("copied");
    } catch {
      setCopyState("failed");
    }
  };

  return (
    <span className={`copyable-value ${className ?? ""}`} data-copy-state={copyState} data-copyable-label={label}>
      <span
        className="copyable-value-text"
        onBlur={() => setTooltipPosition(null)}
        onFocus={(event) => showTooltip(event.currentTarget)}
        onMouseEnter={(event) => showTooltip(event.currentTarget)}
        onMouseLeave={() => setTooltipPosition(null)}
        tabIndex={0}
        title={value}
      >
        {displayValue ?? value}
      </span>
      <button aria-label={`Copy ${label}`} className="copy-icon-button" onClick={copy} title={`Copy ${label}`} type="button">
        {copyState === "copied" ? <Check aria-hidden="true" size={13} /> : <Copy aria-hidden="true" size={13} />}
      </button>
      {tooltipPosition ? (
        <span className="copyable-tooltip" role="tooltip" style={{ left: tooltipPosition.left, top: tooltipPosition.top }}>
          {value}
        </span>
      ) : null}
      {copyState !== "idle" ? <span className="copy-state-text">{copyState === "copied" ? "Copied" : "Copy failed"}</span> : null}
    </span>
  );
}

async function copyText(value: string) {
  if (navigator.clipboard) {
    await navigator.clipboard.writeText(value);
    return;
  }
  const textArea = document.createElement("textarea");
  textArea.value = value;
  textArea.style.position = "fixed";
  textArea.style.opacity = "0";
  document.body.appendChild(textArea);
  textArea.focus();
  textArea.select();
  try {
    document.execCommand("copy");
  } finally {
    document.body.removeChild(textArea);
  }
}
