<script lang="ts">
	import { X } from 'lucide-svelte';
	import type { ItemTagColor } from '@colectivo/types';

	/**
	 * Small pill that renders an item tag.
	 *
	 *   - default: display-only `<span>`
	 *   - `onRemove`: renders the pill as a `<span>` with an inline X button
	 *   - `onSelect`: renders the pill as a single `<button>` (used by the
	 *     filter bar and item-row chips that filter the list on click)
	 *
	 * `onSelect` and `onRemove` are mutually exclusive — supplying both is a
	 * programming error (nested `<button>` is invalid HTML and SvelteKit
	 * warns about hydration mismatches). The picker-selected variant uses
	 * `onRemove`; the filter-bar variant uses `onSelect`.
	 */
	interface Props {
		name: string;
		color: ItemTagColor;
		onRemove?: () => void;
		onSelect?: () => void;
		active?: boolean;
		testid?: string;
	}

	const { name, color, onRemove, onSelect, active = false, testid }: Props = $props();

	// Tailwind cannot see dynamic class names — see tailwind.config.ts safelist.
	const bg = $derived(`bg-${color}-100 dark:bg-${color}-900/40`);
	const fg = $derived(`text-${color}-700 dark:text-${color}-200`);
	const ring = $derived(active ? `ring-1 ring-${color}-200 dark:ring-${color}-700/50` : '');
	const baseClasses = $derived(
		`inline-flex items-center gap-1 rounded-full px-2 py-0.5 text-xs font-medium ${bg} ${fg} ${ring}`
	);
</script>

{#if onSelect}
	<button
		type="button"
		onclick={onSelect}
		data-testid={testid ?? 'tag-chip'}
		data-tag={name}
		data-active={active ? 'true' : undefined}
		class="{baseClasses} transition-opacity hover:opacity-90"
	>
		<span class="truncate">{name}</span>
	</button>
{:else}
	<span
		data-testid={testid ?? 'tag-chip'}
		data-tag={name}
		class={baseClasses}
	>
		<span class="truncate">{name}</span>
		{#if onRemove}
			<button
				type="button"
				onclick={onRemove}
				aria-label="Remove"
				class="-mr-0.5 rounded-full p-0.5 hover:bg-black/10 dark:hover:bg-white/10"
			>
				<X size={10} strokeWidth={2} />
			</button>
		{/if}
	</span>
{/if}
