5e builder: add curated official subclasses (start with Rogue Mastermind)

classes.json ships the SRD subclass + third-party homebrew but is missing most official
PHB/XGE archetypes. New DND5E_SUBCLASSES supplement is merged (deduped by name) ahead of
the on-disk list in the builder, surviving any classes.json regeneration. First entry:
Rogue → Mastermind. (Subclass feature mechanics remain a separate task; this adds the
selectable options.)

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
2026-06-09 22:34:49 +02:00
parent ba26a9d41b
commit 86cc3191ca
2 changed files with 22 additions and 1 deletions
@@ -18,6 +18,7 @@ import { getClassTip, raceSynergyNote } from '@/lib/assistant/builder';
import { briefOverview, dedupeByName } from './overview';
import { parseAsiBonuses, makeSkillResolver, parseBackgroundSkills, parseTraitSkills } from './origin';
import { PF2E_SUBCLASSES } from '@/lib/rules/pf2e/progression';
import { DND5E_SUBCLASSES } from '@/lib/rules/dnd5e/progression';
import { Modal } from '@/components/ui/Modal';
import { Button } from '@/components/ui/Button';
import { Badge } from '@/components/ui/Codex';
@@ -94,7 +95,14 @@ export function CreationWizard({ campaign, onClose }: { campaign: Campaign; onCl
const caster = def && def.caster !== 'none' && def.spellAbility ? def.spellAbility : rc.caster;
return { ...rc, caster, subclasses };
})
: c;
: c.map((rc) => {
// Merge curated official subclasses (classes.json is missing most PHB/XGE
// archetypes) ahead of the on-disk list, deduped by name.
const extra = DND5E_SUBCLASSES[rc.name] ?? [];
if (!extra.length) return rc;
const have = new Set(rc.subclasses.map((s) => s.name.toLowerCase()));
return { ...rc, subclasses: [...extra.filter((s) => !have.has(s.name.toLowerCase())), ...rc.subclasses] };
});
setClasses([...enriched].sort((a, b) => a.name.localeCompare(b.name)));
});
return () => { on = false; };
+13
View File
@@ -99,3 +99,16 @@ export function dnd5eAsiLevels(className: string): number[] {
if (c === 'rogue') return [...base, 10].sort((a, b) => a - b);
return base;
}
/**
* Curated official 5e subclasses, merged into the builder's class list on top of
* whatever the on-disk classes.json carries (which is SRD + third-party homebrew and
* is missing most PHB/XGE archetypes). Keyed by class name; deduped by name at merge
* time. Descriptions are short "what it plays like" blurbs — subclass *features* are
* not yet auto-applied (a separate task), so these add the missing options to pick.
*/
export const DND5E_SUBCLASSES: Record<string, { name: string; desc: string }[]> = {
Rogue: [
{ name: 'Mastermind', desc: 'A master of intrigue and tactics: extra tool/language proficiencies, Help as a bonus action at range, and uncanny insight into a creatures drives.' },
],
};