"use client";

import type { MatrixGroupConfig, FieldType } from "@/types/form";
import type { UseFormRegister, FieldValues } from "react-hook-form";

interface MatrixGroupProps {
  group: MatrixGroupConfig;
  register: UseFormRegister<FieldValues>;
}

/**
 * Renders a matrix of repeating fields as an HTML table.
 *
 * - Row labels live in the leftmost column (sticky on horizontal scroll).
 * - Column headers carry the period labels (M1..M12, Q1..Q4, …).
 * - Each row's `type` controls the cell input rendering: currency cells get
 *   a $ prefix on the row label rather than per-cell to save space; percent
 *   cells append %.
 * - On narrow viewports the table scrolls horizontally; the metric column
 *   stays pinned via position:sticky.
 *
 * Cells are still individual react-hook-form fields, registered by
 * `field.fields[colIndex]`. The matrix only changes layout — submission and
 * validation behave exactly like the standalone-input version.
 */
export function MatrixGroup({ group, register }: MatrixGroupProps) {
  return (
    <section
      aria-labelledby={`${group.id}-heading`}
      className="rounded-xl border border-stone-200 bg-white p-4 shadow-sm sm:p-5"
    >
      <header className="mb-3">
        <h3 id={`${group.id}-heading`} className="text-base font-semibold text-stone-900">
          {group.label}
        </h3>
        {group.intro && (
          <p className="mt-1 text-sm text-stone-600 leading-relaxed">{group.intro}</p>
        )}
      </header>

      <div className="overflow-x-auto -mx-4 sm:mx-0">
        <table className="min-w-full border-separate border-spacing-0 text-sm">
          <thead>
            <tr>
              <th
                scope="col"
                className="sticky left-0 z-10 bg-stone-50 border-b border-stone-200 px-3 py-2 text-left font-medium text-stone-700"
              >
                Metric
              </th>
              {group.cols.map((c) => (
                <th
                  key={c.key}
                  scope="col"
                  className="border-b border-stone-200 bg-stone-50 px-2 py-2 text-center font-medium text-stone-700 min-w-[5.5rem]"
                >
                  {c.label}
                </th>
              ))}
            </tr>
          </thead>
          <tbody>
            {group.rows.map((row, rowIdx) => (
              <tr key={rowIdx} className={rowIdx % 2 === 0 ? "bg-white" : "bg-stone-50/40"}>
                <th
                  scope="row"
                  className="sticky left-0 z-10 border-b border-stone-100 bg-inherit px-3 py-1.5 text-left font-medium text-stone-800 whitespace-nowrap"
                >
                  {decoratedRowLabel(row.label, row.type)}
                </th>
                {row.fields.map((fieldName, colIdx) => (
                  <td
                    key={`${rowIdx}-${colIdx}`}
                    className="border-b border-stone-100 px-1 py-1"
                  >
                    <CellInput
                      fieldName={fieldName}
                      type={row.type}
                      label={`${row.label} ${group.cols[colIdx]?.label ?? ""}`.trim()}
                      register={register}
                    />
                  </td>
                ))}
              </tr>
            ))}
          </tbody>
        </table>
      </div>
    </section>
  );
}

function decoratedRowLabel(label: string, type: FieldType): string {
  if (type === "currency") return `${label} ($)`;
  if (type === "percent") return `${label} (%)`;
  return label;
}

interface CellInputProps {
  fieldName: string;
  type: FieldType;
  label: string; // for aria-label only
  register: UseFormRegister<FieldValues>;
}

/**
 * A compact, table-cell-sized input. No visible label (the row + column
 * already provide context); a screen-reader label is set via aria-label.
 * Supports currency / percent / number / text — uniform sizing across cells.
 */
function CellInput({ fieldName, type, label, register }: CellInputProps) {
  const isNumeric = type === "currency" || type === "percent" || type === "number";
  const baseClass =
    "w-full rounded border border-stone-200 bg-white px-2 py-1 text-right text-stone-900 " +
    "tabular-nums shadow-sm transition " +
    "focus:border-leaf-500 focus:outline-none focus:ring-2 focus:ring-leaf-500/30";

  if (isNumeric) {
    return (
      <input
        type="number"
        inputMode="decimal"
        aria-label={label}
        step={type === "number" ? 1 : 0.01}
        {...register(fieldName, { valueAsNumber: true })}
        className={baseClass}
      />
    );
  }

  return (
    <input
      type="text"
      aria-label={label}
      {...register(fieldName)}
      className={baseClass + " text-left"}
    />
  );
}
