Add critical data model omissions from rulebook audit

- CharacterData: Add ancestryId reference, studiedDice resource pool,
  and statusEffects array with Countdown Dice support (d6→d4→ends)
- PerkData: Add luckCost/grantsLuck for Luck system integration,
  isRitual/ritualDuration/ritualComponents for ritual perks
- WeaponData/ArmorData/EquipmentData: Add relic schema with tier,
  unique abilities, attunement, uses per day, and lore fields
- Effects helper: Add effect keys for luck.max and studiedDice.max

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
Cal Corum 2025-12-12 15:52:15 -06:00
parent 51f0472d99
commit b975c1070f
6 changed files with 198 additions and 1 deletions

View File

@ -29,6 +29,14 @@ export default class CharacterData extends VagabondActorBase {
return {
...baseSchema,
// Reference to equipped ancestry item (UUID)
ancestryId: new fields.StringField({
required: false,
nullable: true,
blank: true,
initial: null,
}),
// Character level (1-10)
level: new fields.NumberField({
required: true,
@ -200,9 +208,15 @@ export default class CharacterData extends VagabondActorBase {
fatigue: new fields.SchemaField({
value: new fields.NumberField({ integer: true, initial: 0, min: 0, max: 5 }),
}),
// Studied Dice pool (Scholar class feature - d8s that can replace d20 rolls)
studiedDice: new fields.SchemaField({
value: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
max: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
}),
}),
// Custom resources (for class-specific tracking like Studied Dice)
// Custom resources (for class-specific tracking)
customResources: new fields.ArrayField(
new fields.SchemaField({
name: new fields.StringField({ required: true }),
@ -211,6 +225,42 @@ export default class CharacterData extends VagabondActorBase {
})
),
// Status Effects with Countdown Dice support
// Countdown Dice: Track duration with shrinking dice (d6 -> d4 -> ends)
statusEffects: new fields.ArrayField(
new fields.SchemaField({
// Effect name (e.g., "Burning", "Poisoned", "Blessed")
name: new fields.StringField({ required: true }),
// Effect description
description: new fields.StringField({ required: false, blank: true }),
// Source of the effect (item UUID, spell name, etc.)
source: new fields.StringField({ required: false, blank: true }),
// Icon path for display
icon: new fields.StringField({ initial: "icons/svg/aura.svg" }),
// Is this a beneficial or harmful effect?
beneficial: new fields.BooleanField({ initial: false }),
// Duration type: "countdown" (Cd4/Cd6), "rounds", "turns", "permanent"
durationType: new fields.StringField({
initial: "countdown",
choices: ["countdown", "rounds", "turns", "permanent"],
}),
// Current countdown die size (6 = d6, 4 = d4, 0 = ended)
countdownDie: new fields.NumberField({ integer: true, initial: 6, min: 0, max: 12 }),
// For rounds/turns duration: remaining count
durationValue: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
// Active Effect changes to apply while this status is active
changes: new fields.ArrayField(
new fields.SchemaField({
key: new fields.StringField({ required: true }),
mode: new fields.NumberField({ integer: true, initial: 2 }),
value: new fields.StringField({ required: true }),
}),
{ initial: [] }
),
}),
{ initial: [] }
),
// Armor value (from equipped armor)
armor: new fields.NumberField({ integer: true, initial: 0, min: 0 }),

View File

@ -68,6 +68,44 @@ export default class ArmorData extends VagabondItemBase {
// Special properties or enchantments
properties: new fields.ArrayField(new fields.StringField(), { initial: [] }),
// Relic System - Powerful magic items with unique abilities
relic: new fields.SchemaField({
// Is this item a relic?
isRelic: new fields.BooleanField({ initial: false }),
// Relic tier (determines power level)
tier: new fields.NumberField({
integer: true,
initial: 1,
min: 1,
max: 5,
}),
// Unique ability name
abilityName: new fields.StringField({ required: false, blank: true }),
// Unique ability description
abilityDescription: new fields.HTMLField({ required: false, blank: true }),
// Activation cost (mana, luck, etc.)
activationCost: new fields.StringField({ required: false, blank: true }),
// Uses per day (0 = unlimited or passive)
usesPerDay: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
// Current uses remaining
usesRemaining: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
// Attunement required?
requiresAttunement: new fields.BooleanField({ initial: false }),
// Currently attuned?
attuned: new fields.BooleanField({ initial: false }),
// Lore/history of the relic
lore: new fields.HTMLField({ required: false, blank: true }),
}),
};
}

View File

@ -76,6 +76,44 @@ export default class EquipmentData extends VagabondItemBase {
// Tags for filtering/searching
tags: new fields.ArrayField(new fields.StringField(), { initial: [] }),
// Relic System - Powerful magic items with unique abilities
relic: new fields.SchemaField({
// Is this item a relic?
isRelic: new fields.BooleanField({ initial: false }),
// Relic tier (determines power level)
tier: new fields.NumberField({
integer: true,
initial: 1,
min: 1,
max: 5,
}),
// Unique ability name
abilityName: new fields.StringField({ required: false, blank: true }),
// Unique ability description
abilityDescription: new fields.HTMLField({ required: false, blank: true }),
// Activation cost (mana, luck, etc.)
activationCost: new fields.StringField({ required: false, blank: true }),
// Uses per day (0 = unlimited or passive)
usesPerDay: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
// Current uses remaining
usesRemaining: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
// Attunement required?
requiresAttunement: new fields.BooleanField({ initial: false }),
// Currently attuned?
attuned: new fields.BooleanField({ initial: false }),
// Lore/history of the relic
lore: new fields.HTMLField({ required: false, blank: true }),
}),
};
}

View File

@ -72,6 +72,37 @@ export default class PerkData extends VagabondItemBase {
per: new fields.StringField({ initial: "" }), // "short", "long", "day", ""
}),
// Luck System Integration
// Cost in Luck points to activate this perk
luckCost: new fields.NumberField({
integer: true,
initial: 0,
min: 0,
}),
// Does this perk grant Luck when triggered?
grantsLuck: new fields.NumberField({
integer: true,
initial: 0,
min: 0,
}),
// Ritual System (specific perks are rituals with extended casting)
isRitual: new fields.BooleanField({ initial: false }),
// Ritual duration in minutes (10, 60, etc.)
ritualDuration: new fields.NumberField({
integer: true,
initial: 0,
min: 0,
}),
// Ritual components required (text description)
ritualComponents: new fields.StringField({
required: false,
blank: true,
}),
// Tags for categorization
tags: new fields.ArrayField(new fields.StringField(), { initial: [] }),
};

View File

@ -121,6 +121,44 @@ export default class WeaponData extends VagabondItemBase {
min: 1,
max: 20,
}),
// Relic System - Powerful magic items with unique abilities
relic: new fields.SchemaField({
// Is this item a relic?
isRelic: new fields.BooleanField({ initial: false }),
// Relic tier (determines power level)
tier: new fields.NumberField({
integer: true,
initial: 1,
min: 1,
max: 5,
}),
// Unique ability name
abilityName: new fields.StringField({ required: false, blank: true }),
// Unique ability description
abilityDescription: new fields.HTMLField({ required: false, blank: true }),
// Activation cost (mana, luck, etc.)
activationCost: new fields.StringField({ required: false, blank: true }),
// Uses per day (0 = unlimited or passive)
usesPerDay: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
// Current uses remaining
usesRemaining: new fields.NumberField({ integer: true, initial: 0, min: 0 }),
// Attunement required?
requiresAttunement: new fields.BooleanField({ initial: false }),
// Currently attuned?
attuned: new fields.BooleanField({ initial: false }),
// Lore/history of the relic
lore: new fields.HTMLField({ required: false, blank: true }),
}),
};
}

View File

@ -41,6 +41,8 @@ export const EFFECT_KEYS = {
"hp.bonus": "system.resources.hp.bonus",
"mana.bonus": "system.resources.mana.bonus",
"mana.castingMax": "system.resources.mana.castingMax",
"luck.max": "system.resources.luck.max",
"studiedDice.max": "system.resources.studiedDice.max",
"speed.bonus": "system.speed.bonus",
armor: "system.armor",
"itemSlots.bonus": "system.itemSlots.bonus",