Combat: condition dropdown picker with tag chips

- System-aware condition list (5e PHB / pf2e) in src/lib/rules/conditions.ts
- Dropdown replaces free-text input; non-valued conditions add instantly,
  valued ones (Exhaustion, Frightened N, etc.) show a value field, plus Custom
- Already-applied conditions disabled in the list; chips remain click-to-remove
- New e2e covering preset + valued add and tag removal

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-06-08 00:44:37 +02:00
parent 866f1e1bf1
commit 0b356adf82
5 changed files with 194 additions and 19 deletions
+66
View File
@@ -0,0 +1,66 @@
import type { SystemId } from './types';
export interface ConditionDef {
name: string;
/** true for conditions that carry a numeric value (e.g. PF2e Frightened 2). */
valued: boolean;
}
/** D&D 5e conditions (PHB). Exhaustion is the only valued one. */
export const CONDITIONS_5E: readonly ConditionDef[] = [
{ name: 'Blinded', valued: false },
{ name: 'Charmed', valued: false },
{ name: 'Concentrating', valued: false },
{ name: 'Deafened', valued: false },
{ name: 'Exhaustion', valued: true },
{ name: 'Frightened', valued: false },
{ name: 'Grappled', valued: false },
{ name: 'Incapacitated', valued: false },
{ name: 'Invisible', valued: false },
{ name: 'Paralyzed', valued: false },
{ name: 'Petrified', valued: false },
{ name: 'Poisoned', valued: false },
{ name: 'Prone', valued: false },
{ name: 'Restrained', valued: false },
{ name: 'Stunned', valued: false },
{ name: 'Unconscious', valued: false },
];
/** Pathfinder 2e conditions. Many carry a value. */
export const CONDITIONS_PF2E: readonly ConditionDef[] = [
{ name: 'Blinded', valued: false },
{ name: 'Clumsy', valued: true },
{ name: 'Concealed', valued: false },
{ name: 'Confused', valued: false },
{ name: 'Controlled', valued: false },
{ name: 'Dazzled', valued: false },
{ name: 'Deafened', valued: false },
{ name: 'Doomed', valued: true },
{ name: 'Drained', valued: true },
{ name: 'Dying', valued: true },
{ name: 'Enfeebled', valued: true },
{ name: 'Fascinated', valued: false },
{ name: 'Fatigued', valued: false },
{ name: 'Fleeing', valued: false },
{ name: 'Frightened', valued: true },
{ name: 'Grabbed', valued: false },
{ name: 'Immobilized', valued: false },
{ name: 'Invisible', valued: false },
{ name: 'Off-Guard', valued: false },
{ name: 'Paralyzed', valued: false },
{ name: 'Persistent Damage', valued: true },
{ name: 'Petrified', valued: false },
{ name: 'Prone', valued: false },
{ name: 'Quickened', valued: false },
{ name: 'Restrained', valued: false },
{ name: 'Sickened', valued: true },
{ name: 'Slowed', valued: true },
{ name: 'Stunned', valued: true },
{ name: 'Stupefied', valued: true },
{ name: 'Unconscious', valued: false },
{ name: 'Wounded', valued: true },
];
export function getConditions(system: SystemId): readonly ConditionDef[] {
return system === 'pf2e' ? CONDITIONS_PF2E : CONDITIONS_5E;
}
+1
View File
@@ -19,3 +19,4 @@ export const SYSTEM_OPTIONS: { id: SystemId; label: string }[] = [
export * from './types';
export { abilityModifier, ABILITY_ABBR, ABILITY_LABELS, formatDamage } from './abilities';
export { applyRest } from './rest';
export { getConditions, CONDITIONS_5E, CONDITIONS_PF2E, type ConditionDef } from './conditions';