Levelup Followup (#126)

* Levelup applies bonuses to character

* Added visualisation of domain card levels

* Fixed domaincard level max for selections in a tier

* A trait can now only be level up once within the same tier
This commit is contained in:
WBHarry 2025-06-13 14:15:02 +02:00 committed by GitHub
parent f840dc2553
commit ec3aecfe99
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
23 changed files with 566 additions and 202 deletions

View file

@ -17,7 +17,6 @@ export default class DHClass extends BaseDataItem {
return {
...super.defineSchema(),
domains: new fields.ArrayField(new fields.StringField(), { max: 2 }),
classItems: new fields.ArrayField(new ForeignDocumentUUIDField({ type: 'Item' })),
evasion: new fields.NumberField({ initial: 0, integer: true }),
features: new fields.ArrayField(new ForeignDocumentUUIDField({ type: 'Item' })),

View file

@ -36,17 +36,12 @@ export default class DHDomainCard extends BaseDataItem {
return false;
}
if (!this.actor.system.domains.find(x => x === item.system.domain)) {
if (!this.actor.system.domains.find(x => x === this.domain)) {
ui.notifications.error(game.i18n.localize('DAGGERHEART.Item.Errors.LacksDomain'));
return false;
}
if (this.actor.system.domainCards.total.length === 5) {
ui.notifications.error(game.i18n.localize('DAGGERHEART.Item.Errors.MaxLoadoutReached'));
return false;
}
if (this.actor.system.domainCards.total.find(x => x.name === item.name)) {
if (this.actor.system.domainCards.total.find(x => x.name === this.parent.name)) {
ui.notifications.error(game.i18n.localize('DAGGERHEART.Item.Errors.DuplicateDomainCard'));
return false;
}

View file

@ -25,24 +25,37 @@ export default class DHSubclass extends BaseDataItem {
foundationFeature: new ForeignDocumentUUIDField({ type: 'Item' }),
specializationFeature: new ForeignDocumentUUIDField({ type: 'Item' }),
masteryFeature: new ForeignDocumentUUIDField({ type: 'Item' }),
featureState: new fields.NumberField({ required: true, initial: 1, min: 1 }),
isMulticlass: new fields.BooleanField({ initial: false })
};
}
get features() {
return {
foundation: this.foundationFeature,
specialization: this.featureState >= 2 ? this.specializationFeature : null,
mastery: this.featureState === 3 ? this.masteryFeature : null
};
}
async _preCreate(data, options, user) {
const allowed = await super._preCreate(data, options, user);
if (allowed === false) return;
if (this.actor?.type === 'character') {
const path = data.system.isMulticlass ? 'system.multiclass' : 'system.class';
const classData = foundry.utils.getProperty(this.actor, path);
if (!classData.value) {
const classData = this.actor.items.find(
x => x.type === 'class' && x.system.isMulticlass === data.system.isMulticlass
);
const subclassData = this.actor.items.find(
x => x.type === 'subclass' && x.system.isMulticlass === data.system.isMulticlass
);
if (!classData) {
ui.notifications.error(game.i18n.localize('DAGGERHEART.Item.Errors.MissingClass'));
return false;
} else if (classData.subclass) {
} else if (subclassData) {
ui.notifications.error(game.i18n.localize('DAGGERHEART.Item.Errors.SubclassAlreadySelected'));
return false;
} else if (classData.value.system.subclasses.every(x => x.uuid !== `Item.${data._id}`)) {
} else if (classData.system.subclasses.every(x => x.uuid !== `Item.${data._id}`)) {
ui.notifications.error(game.i18n.localize('DAGGERHEART.Item.Errors.SubclassNotInClass'));
return false;
}