import { ProBadge } from "@/components/plan-badges";
import { Badge } from "@/components/ui/badge";
import { Switch } from "@/components/ui/switch";
import { IS_PRO } from "@/lib/env";
import { cn } from "@/lib/utils";
import { __, sprintf } from "@wordpress/i18n";
import { GripVertical, SlidersHorizontal, X } from "lucide-react";
import { useState } from "react";
import { KINDS } from "../constants";
import RowOptions from "./RowOptions";

/**
 * One table row: drag handle (pointer drag, or Arrow Up/Down), name, type
 * badge, Pro badge and on/off switch. Header rows have no handle. Pro rows
 * are locked in Free. Rows added by hand (custom fields) can be removed.
 */
const FieldRow = ({
  field,
  index,
  total,
  handle,
  dragging,
  line,
  onKeyMove,
  onToggle,
  onRemove,
}) => {
  const [open, setOpen] = useState(false);
  const name = field.label || field.default_label || field.key;
  const locked = field.pro && !IS_PRO;

  const onKeyDown = (event) => {
    if (event.key === "ArrowUp" || event.key === "ArrowDown") {
      event.preventDefault();
      onKeyMove(
        index,
        index + (event.key === "ArrowUp" ? -1 : 1),
        event.currentTarget,
      );
    }
  };

  return (
    <li
      className={cn(
        "ino:relative ino:flex ino:flex-wrap ino:items-center ino:gap-3 ino:rounded-lg ino:border ino:border-border ino:bg-background ino:px-2.5 ino:py-2",
        dragging && "ino:z-10 ino:border-primary ino:opacity-70 ino:shadow-md",
        line === "before" &&
          "ino:before:absolute ino:before:inset-x-0 ino:before:-top-[5px] ino:before:h-0.5 ino:before:rounded-full ino:before:bg-primary",
        line === "after" &&
          "ino:after:absolute ino:after:inset-x-0 ino:after:-bottom-[5px] ino:after:h-0.5 ino:after:rounded-full ino:after:bg-primary",
      )}
    >
      {handle ? (
        <button
          type="button"
          {...handle}
          onKeyDown={onKeyDown}
          aria-label={sprintf(
            /* translators: 1: row name, 2: position, 3: number of rows */
            __(
              "Reorder %1$s, position %2$d of %3$d. Drag, or use arrow up or down.",
              "product-comparison-for-woocommerce",
            ),
            name,
            index + 1,
            total,
          )}
          className="ino:flex ino:size-8 ino:cursor-grab ino:items-center ino:justify-center ino:rounded-md ino:text-muted-foreground ino:select-none ino:hover:bg-muted ino:focus-visible:ring-3 ino:focus-visible:ring-ring/50 ino:focus-visible:outline-none ino:active:cursor-grabbing"
        >
          <GripVertical size={16} aria-hidden="true" />
        </button>
      ) : (
        <span className="ino:size-8" aria-hidden="true" />
      )}
      <div className="ino:flex ino:min-w-0 ino:flex-1 ino:flex-wrap ino:items-center ino:gap-2">
        <span
          className={cn(
            "ino:text-sm ino:font-medium",
            locked && "ino:text-muted-foreground",
          )}
        >
          {name}
        </span>
        <Badge variant="secondary">{KINDS[field.type] ?? field.type}</Badge>
        {field.pro && <ProBadge />}
      </div>
      <button
        type="button"
        aria-expanded={open}
        onClick={() => setOpen(!open)}
        aria-label={sprintf(
          /* translators: %s: row name */
          __("Options for %s", "product-comparison-for-woocommerce"),
          name,
        )}
        className={cn(
          "ino:flex ino:size-8 ino:items-center ino:justify-center ino:rounded-md ino:text-muted-foreground ino:hover:bg-muted ino:hover:text-foreground ino:focus-visible:ring-3 ino:focus-visible:ring-ring/50 ino:focus-visible:outline-none",
          open && "ino:bg-muted ino:text-foreground",
        )}
      >
        <SlidersHorizontal size={15} aria-hidden="true" />
      </button>
      <Switch
        aria-label={sprintf(
          /* translators: %s: row name */
          __("Show %s", "product-comparison-for-woocommerce"),
          name,
        )}
        checked={field.enabled && !locked}
        disabled={locked}
        onCheckedChange={() => onToggle(field.key)}
      />
      {onRemove && (
        <button
          type="button"
          onClick={() => onRemove(field.key)}
          aria-label={sprintf(
            /* translators: %s: row name */
            __("Remove %s", "product-comparison-for-woocommerce"),
            name,
          )}
          className="ino:flex ino:size-8 ino:items-center ino:justify-center ino:rounded-md ino:text-muted-foreground ino:hover:bg-muted ino:hover:text-foreground ino:focus-visible:ring-3 ino:focus-visible:ring-ring/50 ino:focus-visible:outline-none"
        >
          <X size={15} aria-hidden="true" />
        </button>
      )}
      {open && <RowOptions field={field} />}
    </li>
  );
};

export default FieldRow;
