import { useState } from "react";
import { InlineSelect } from "~/ui/Field";
import { updateProjectItem } from "~/fns/projects";
import { useAction } from "~/hooks/use-action";
import { ItemTitle } from "./ItemTitle";
import type { ProjectData, ProjectField } from "./ItemTitle";
import { EmptyState } from "~/ui/EmptyState";
import { cn } from "~/utils/cn";
import { CountBadge } from "~/ui/CountBadge";
const NO_VALUE = "";
/** Kanban columns over a single-select field; cards move between columns with native drag-and-drop. */
export function ProjectBoard({ data, field }: { data: ProjectData; field: ProjectField | undefined }) {
const update = useAction(updateProjectItem);
const [over, setOver] = useState<string | null>(null);
if (!field) return <EmptyState title="Add a single-select field to use the board view" icon="project" />;
const columns = [NO_VALUE, ...field.options];
const projectRef = { owner: data.project.owner, number: data.project.number };
function drop(column: string, itemId: string) {
setOver(null);
const item = data.items.find((candidate) => candidate.id === itemId);
if (!item || !field || (item.values[field.id] ?? NO_VALUE) === column) return;
const last = Math.max(0, ...data.items.map((candidate) => candidate.position));
void update.run({
data: { ...projectRef, itemId, fieldId: field.id, value: column || null, position: last + 1 },
});
}
return (
<div className="space-y-2">
{update.error && <p className="text-xs text-kumo-danger">{update.error}</p>}
<div className="flex gap-3 overflow-x-auto p-3">
{columns.map((column) => {
const cards = data.items.filter((item) => (item.values[field.id] ?? NO_VALUE) === column);
return (
// oxlint-disable-next-line jsx-a11y/no-noninteractive-element-interactions -- drag is a pointer shortcut; each card's select is the keyboard path
<section
key={column || "none"}