Add Pathfinder 2e game system mode
Implements PF2e as an alternative game system alongside D&D 5e/5.5e. Settings modal "Game System" selector switches conditions, bestiary, stat block layout, and initiative calculation between systems. - Valued conditions with increment/decrement UX (Clumsy 2, Frightened 3) - 2,502 PF2e creatures from bundled search index (77 sources) - PF2e stat block: level, traits, Perception, Fort/Ref/Will, ability mods - Perception-based initiative rolling - System-scoped source cache (D&D and PF2e sources don't collide) - Backwards-compatible condition rehydration (ConditionId[] → ConditionEntry[]) - Difficulty indicator hidden in PF2e mode (excluded from MVP) Closes dostulata/initiative#19 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -26,25 +26,40 @@ describe("getConditionDescription", () => {
|
||||
);
|
||||
});
|
||||
|
||||
it("universal conditions have both descriptions", () => {
|
||||
const universal = CONDITION_DEFINITIONS.filter(
|
||||
(d) => d.edition === undefined,
|
||||
it("returns pf2e description when edition is pf2e", () => {
|
||||
const blinded = findCondition("blinded");
|
||||
expect(getConditionDescription(blinded, "pf2e")).toBe(
|
||||
blinded.descriptionPf2e,
|
||||
);
|
||||
expect(universal.length).toBeGreaterThan(0);
|
||||
for (const def of universal) {
|
||||
expect(def.description).toBeTruthy();
|
||||
expect(def.description5e).toBeTruthy();
|
||||
});
|
||||
|
||||
it("falls back to default description for pf2e when no pf2e text", () => {
|
||||
const paralyzed = findCondition("paralyzed");
|
||||
expect(getConditionDescription(paralyzed, "pf2e")).toBe(
|
||||
paralyzed.descriptionPf2e,
|
||||
);
|
||||
});
|
||||
|
||||
it("shared D&D conditions have both description and description5e", () => {
|
||||
const sharedDndConditions = CONDITION_DEFINITIONS.filter(
|
||||
(d) =>
|
||||
d.systems === undefined ||
|
||||
(d.systems.includes("5e") && d.systems.includes("5.5e")),
|
||||
);
|
||||
for (const def of sharedDndConditions) {
|
||||
expect(def.description, `${def.id} missing description`).toBeTruthy();
|
||||
expect(def.description5e, `${def.id} missing description5e`).toBeTruthy();
|
||||
}
|
||||
});
|
||||
|
||||
it("edition-specific conditions have their edition description", () => {
|
||||
it("system-specific conditions use the systems field", () => {
|
||||
const sapped = findCondition("sapped");
|
||||
expect(sapped.description).toBeTruthy();
|
||||
expect(sapped.edition).toBe("5.5e");
|
||||
expect(sapped.systems).toContain("5.5e");
|
||||
|
||||
const slowed = findCondition("slowed");
|
||||
expect(slowed.description).toBeTruthy();
|
||||
expect(slowed.edition).toBe("5.5e");
|
||||
expect(slowed.systems).toContain("5.5e");
|
||||
});
|
||||
|
||||
it("conditions with identical rules share the same text", () => {
|
||||
@@ -79,4 +94,34 @@ describe("getConditionsForEdition", () => {
|
||||
expect(ids5e).toContain("blinded");
|
||||
expect(ids55e).toContain("blinded");
|
||||
});
|
||||
|
||||
it("returns PF2e conditions for pf2e edition", () => {
|
||||
const conditions = getConditionsForEdition("pf2e");
|
||||
const ids = conditions.map((d) => d.id);
|
||||
expect(ids).toContain("clumsy");
|
||||
expect(ids).toContain("drained");
|
||||
expect(ids).toContain("off-guard");
|
||||
expect(ids).toContain("sickened");
|
||||
expect(ids).not.toContain("charmed");
|
||||
expect(ids).not.toContain("exhaustion");
|
||||
expect(ids).not.toContain("grappled");
|
||||
});
|
||||
|
||||
it("returns D&D conditions for 5.5e", () => {
|
||||
const conditions = getConditionsForEdition("5.5e");
|
||||
const ids = conditions.map((d) => d.id);
|
||||
expect(ids).toContain("charmed");
|
||||
expect(ids).toContain("exhaustion");
|
||||
expect(ids).not.toContain("clumsy");
|
||||
expect(ids).not.toContain("off-guard");
|
||||
});
|
||||
|
||||
it("shared conditions appear in both D&D and PF2e", () => {
|
||||
const dndIds = getConditionsForEdition("5.5e").map((d) => d.id);
|
||||
const pf2eIds = getConditionsForEdition("pf2e").map((d) => d.id);
|
||||
expect(dndIds).toContain("blinded");
|
||||
expect(pf2eIds).toContain("blinded");
|
||||
expect(dndIds).toContain("prone");
|
||||
expect(pf2eIds).toContain("prone");
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user