mirror of
https://github.com/Foundryborne/daggerheart.git
synced 2026-06-06 04:44:16 +02:00
Merged with main
This commit is contained in:
commit
d78927d0c2
275 changed files with 5076 additions and 4132 deletions
|
|
@ -1,6 +1,6 @@
|
|||
import BaseDataItem from './base.mjs';
|
||||
import ItemLinkFields from '../../data/fields/itemLinkFields.mjs';
|
||||
import { getFeaturesHTMLData } from '../../helpers/utils.mjs';
|
||||
import { fromUuids, getFeaturesHTMLData } from '../../helpers/utils.mjs';
|
||||
|
||||
export default class DHAncestry extends BaseDataItem {
|
||||
/** @inheritDoc */
|
||||
|
|
@ -45,6 +45,10 @@ export default class DHAncestry extends BaseDataItem {
|
|||
|
||||
/**@inheritdoc */
|
||||
async getDescriptionData() {
|
||||
// Preload all ancestry features for acquisition from the cache
|
||||
// todo: make feature acquisition async and replace feature helpers for methods
|
||||
await fromUuids(this._source.features.map(f => f.item));
|
||||
|
||||
const baseDescription = this.description;
|
||||
const features = await getFeaturesHTMLData(this.features);
|
||||
|
||||
|
|
|
|||
|
|
@ -141,16 +141,6 @@ export default class DHArmor extends AttachableItem {
|
|||
}
|
||||
}
|
||||
|
||||
_onUpdate(a, b, c) {
|
||||
super._onUpdate(a, b, c);
|
||||
|
||||
if (this.actor?.type === 'character') {
|
||||
for (const party of this.actor.parties) {
|
||||
party.render();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** @inheritDoc */
|
||||
static migrateDocumentData(source) {
|
||||
if (!source.system.armor) {
|
||||
|
|
|
|||
|
|
@ -7,7 +7,12 @@
|
|||
* @property {boolean} isInventoryItem- Indicates whether items of this type is a Inventory Item
|
||||
*/
|
||||
|
||||
import { addLinkedItemsDiff, getScrollTextData, updateLinkedItemApps } from '../../helpers/utils.mjs';
|
||||
import {
|
||||
addLinkedItemsDiff,
|
||||
getScrollTextData,
|
||||
createShallowProxy,
|
||||
updateLinkedItemApps
|
||||
} from '../../helpers/utils.mjs';
|
||||
import { ActionsField } from '../fields/actionField.mjs';
|
||||
import FormulaField from '../fields/formulaField.mjs';
|
||||
|
||||
|
|
@ -159,8 +164,8 @@ export default class BaseDataItem extends foundry.abstract.TypeDataModel {
|
|||
* @returns {object}
|
||||
*/
|
||||
getRollData(options = {}) {
|
||||
const actorRollData = this.actor?.getRollData() ?? {};
|
||||
const data = { ...actorRollData, item: { ...this } };
|
||||
const data = this.actor?.getRollData() ?? {};
|
||||
data.item = createShallowProxy(this);
|
||||
return data;
|
||||
}
|
||||
|
||||
|
|
@ -195,7 +200,7 @@ export default class BaseDataItem extends foundry.abstract.TypeDataModel {
|
|||
const features = [];
|
||||
for (let f of this.features) {
|
||||
const fBase = f.item ?? f;
|
||||
const feature = fBase.system ? fBase : await foundry.utils.fromUuid(fBase.uuid);
|
||||
const feature = fBase.pack ? await foundry.utils.fromUuid(fBase.uuid) : fBase;
|
||||
features.push(
|
||||
foundry.utils.mergeObject(
|
||||
feature.toObject(),
|
||||
|
|
|
|||
|
|
@ -51,7 +51,8 @@ export default class DHBeastform extends BaseDataItem {
|
|||
}),
|
||||
scale: new fields.NumberField({ nullable: false, min: 0.2, max: 3, step: 0.05, initial: 1 }),
|
||||
height: new fields.NumberField({ integer: true, min: 1, initial: null, nullable: true }),
|
||||
width: new fields.NumberField({ integer: true, min: 1, initial: null, nullable: true })
|
||||
width: new fields.NumberField({ integer: true, min: 1, initial: null, nullable: true }),
|
||||
depth: new fields.NumberField({ integer: true, min: 1, initial: null, nullable: true })
|
||||
}),
|
||||
mainTrait: new fields.StringField({
|
||||
required: true,
|
||||
|
|
@ -192,7 +193,8 @@ export default class DHBeastform extends BaseDataItem {
|
|||
tokenSize: {
|
||||
scale: this.parent.parent.prototypeToken.texture.scaleX,
|
||||
height: this.parent.parent.prototypeToken.height,
|
||||
width: this.parent.parent.prototypeToken.width
|
||||
width: this.parent.parent.prototypeToken.width,
|
||||
depth: this.parent.parent.prototypeToken.depth
|
||||
}
|
||||
},
|
||||
advantageOn: this.advantageOn,
|
||||
|
|
@ -211,10 +213,12 @@ export default class DHBeastform extends BaseDataItem {
|
|||
: null;
|
||||
const width = autoTokenSize ?? this.tokenSize.width;
|
||||
const height = autoTokenSize ?? this.tokenSize.height;
|
||||
const depth = autoTokenSize ?? this.tokenSize.depth;
|
||||
|
||||
const prototypeTokenUpdate = {
|
||||
height,
|
||||
width,
|
||||
depth,
|
||||
texture: {
|
||||
src: this.tokenImg,
|
||||
scaleX: this.tokenSize.scale,
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@ import BaseDataItem from './base.mjs';
|
|||
import ForeignDocumentUUIDField from '../fields/foreignDocumentUUIDField.mjs';
|
||||
import ForeignDocumentUUIDArrayField from '../fields/foreignDocumentUUIDArrayField.mjs';
|
||||
import ItemLinkFields from '../fields/itemLinkFields.mjs';
|
||||
import { addLinkedItemsDiff, getFeaturesHTMLData, updateLinkedItemApps } from '../../helpers/utils.mjs';
|
||||
import { addLinkedItemsDiff, fromUuids, getFeaturesHTMLData, updateLinkedItemApps } from '../../helpers/utils.mjs';
|
||||
import { DhLevelOption } from '../levelTier.mjs';
|
||||
|
||||
export default class DHClass extends BaseDataItem {
|
||||
|
|
@ -32,7 +32,6 @@ export default class DHClass extends BaseDataItem {
|
|||
}),
|
||||
evasion: new fields.NumberField({ initial: 0, integer: true, label: 'DAGGERHEART.GENERAL.evasion' }),
|
||||
features: new ItemLinkFields(),
|
||||
subclasses: new ForeignDocumentUUIDArrayField({ type: 'Item', required: false }),
|
||||
inventory: new fields.SchemaField({
|
||||
take: new ForeignDocumentUUIDArrayField({ type: 'Item', required: false }),
|
||||
choiceA: new ForeignDocumentUUIDArrayField({ type: 'Item', required: false }),
|
||||
|
|
@ -78,6 +77,25 @@ export default class DHClass extends BaseDataItem {
|
|||
return this.features.filter(x => x.type === CONFIG.DH.ITEM.featureSubTypes.class).map(x => x.item);
|
||||
}
|
||||
|
||||
async fetchSubclasses() {
|
||||
const uuids = [this.parent.uuid, this.parent._stats?.compendiumSource].filter(u => !!u);
|
||||
const subclasses = game.items.filter(x => x.type === 'subclass' && uuids.includes(x.system.linkedClass));
|
||||
for (const pack of game.packs) {
|
||||
const packIds = [];
|
||||
const indexes = await pack.getIndex({ fields: ['system.linkedClass'] });
|
||||
for (const index of indexes) {
|
||||
if (index.type !== 'subclass') continue;
|
||||
if (!uuids.includes(index.system?.linkedClass)) continue;
|
||||
if (subclasses.find(x => x.uuid === index.uuid)) continue;
|
||||
packIds.push(index._id);
|
||||
}
|
||||
|
||||
if (packIds.length > 0) subclasses.push(...(await pack.getDocuments({ _id__in: packIds })));
|
||||
}
|
||||
|
||||
return subclasses;
|
||||
}
|
||||
|
||||
async _preCreate(data, options, user) {
|
||||
if (this.actor?.type === 'character') {
|
||||
const levelupAuto = game.settings.get(CONFIG.DH.id, CONFIG.DH.SETTINGS.gameSettings.Automation).levelupAuto;
|
||||
|
|
@ -207,6 +225,10 @@ export default class DHClass extends BaseDataItem {
|
|||
classItems.push(contentLink.outerHTML);
|
||||
}
|
||||
|
||||
// Preload all class features for acquisition from the cache
|
||||
// todo: make feature acquisition async and replace feature helpers for methods
|
||||
await fromUuids(this._source.features.map(f => f.item));
|
||||
|
||||
const hopeFeatures = await getFeaturesHTMLData(this.hopeFeatures);
|
||||
const classFeatures = await getFeaturesHTMLData(this.classFeatures);
|
||||
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import { getFeaturesHTMLData } from '../../helpers/utils.mjs';
|
||||
import { fromUuids, getFeaturesHTMLData } from '../../helpers/utils.mjs';
|
||||
import ForeignDocumentUUIDArrayField from '../fields/foreignDocumentUUIDArrayField.mjs';
|
||||
import BaseDataItem from './base.mjs';
|
||||
|
||||
|
|
@ -27,6 +27,10 @@ export default class DHCommunity extends BaseDataItem {
|
|||
|
||||
/**@inheritdoc */
|
||||
async getDescriptionData() {
|
||||
// Preload all community features for acquisition from the cache
|
||||
// todo: make feature acquisition async and replace feature helpers for methods
|
||||
await fromUuids(this._source.features);
|
||||
|
||||
const baseDescription = this.description;
|
||||
const features = await getFeaturesHTMLData(this.features);
|
||||
|
||||
|
|
|
|||
|
|
@ -1,5 +1,4 @@
|
|||
import { getFeaturesHTMLData } from '../../helpers/utils.mjs';
|
||||
import ForeignDocumentUUIDField from '../fields/foreignDocumentUUIDField.mjs';
|
||||
import { fromUuids, getFeaturesHTMLData } from '../../helpers/utils.mjs';
|
||||
import ItemLinkFields from '../fields/itemLinkFields.mjs';
|
||||
import BaseDataItem from './base.mjs';
|
||||
|
||||
|
|
@ -28,7 +27,7 @@ export default class DHSubclass extends BaseDataItem {
|
|||
features: new ItemLinkFields(),
|
||||
featureState: new fields.NumberField({ required: true, initial: 1, min: 1 }),
|
||||
isMulticlass: new fields.BooleanField({ initial: false }),
|
||||
linkedClass: new ForeignDocumentUUIDField({ type: 'Item', nullable: true, initial: null })
|
||||
linkedClass: new fields.DocumentUUIDField({ type: 'Item', nullable: true, initial: null })
|
||||
};
|
||||
}
|
||||
|
||||
|
|
@ -56,37 +55,30 @@ export default class DHSubclass extends BaseDataItem {
|
|||
if (allowed === false) return;
|
||||
|
||||
if (this.actor?.type === 'character') {
|
||||
const dataUuid = data.uuid ?? data._stats.compendiumSource ?? `Item.${data._id}`;
|
||||
if (this.actor.system.class.subclass) {
|
||||
if (this.actor.system.multiclass.subclass) {
|
||||
ui.notifications.warn(game.i18n.localize('DAGGERHEART.UI.Notifications.subclassesAlreadyPresent'));
|
||||
return false;
|
||||
} else {
|
||||
const multiclass = this.actor.items.find(x => x.type === 'class' && x.system.isMulticlass);
|
||||
if (!multiclass) {
|
||||
ui.notifications.warn(game.i18n.localize('DAGGERHEART.UI.Notifications.missingMulticlass'));
|
||||
return false;
|
||||
}
|
||||
const { value: actorClass, subclass: existingSubclass } = this.actor.system.class;
|
||||
const { value: multiclass, subclass: existingMultisubclass } = this.actor.system.multiclass;
|
||||
if (!actorClass && !multiclass) {
|
||||
ui.notifications.warn('DAGGERHEART.UI.Notifications.missingClass', { localize: true });
|
||||
return false;
|
||||
}
|
||||
if (existingSubclass && existingMultisubclass) {
|
||||
ui.notifications.warn('DAGGERHEART.UI.Notifications.subclassesAlreadyPresent', { localize: true });
|
||||
return false;
|
||||
}
|
||||
if (existingSubclass && !multiclass) {
|
||||
ui.notifications.warn('DAGGERHEART.UI.Notifications.missingMulticlass', { localize: true });
|
||||
return false;
|
||||
}
|
||||
|
||||
if (multiclass.system.subclasses.every(x => x.uuid !== dataUuid)) {
|
||||
ui.notifications.error(
|
||||
game.i18n.localize('DAGGERHEART.UI.Notifications.subclassNotInMulticlass')
|
||||
);
|
||||
return false;
|
||||
}
|
||||
|
||||
await this.updateSource({ isMulticlass: true });
|
||||
}
|
||||
} else {
|
||||
const actorClass = this.actor.items.find(x => x.type === 'class' && !x.system.isMulticlass);
|
||||
if (!actorClass) {
|
||||
ui.notifications.warn(game.i18n.localize('DAGGERHEART.UI.Notifications.missingClass'));
|
||||
return false;
|
||||
}
|
||||
if (actorClass.system.subclasses.every(x => x.uuid !== dataUuid)) {
|
||||
ui.notifications.error(game.i18n.localize('DAGGERHEART.UI.Notifications.subclassNotInClass'));
|
||||
return false;
|
||||
}
|
||||
const match = [multiclass, actorClass].find(
|
||||
c => c && (c._stats.compendiumSource ?? c.uuid) === this.linkedClass
|
||||
);
|
||||
if (!match) {
|
||||
const key = multiclass ? 'subclassNotInMulticlass' : 'subclassNotInClass';
|
||||
ui.notifications.warn(`DAGGERHEART.UI.Notifications.${key}`, { localize: true });
|
||||
return false;
|
||||
} else if (match.system.isMulticlass) {
|
||||
await this.updateSource({ isMulticlass: true });
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -98,6 +90,11 @@ export default class DHSubclass extends BaseDataItem {
|
|||
const spellcastTrait = this.spellcastingTrait
|
||||
? game.i18n.localize(CONFIG.DH.ACTOR.abilities[this.spellcastingTrait].label)
|
||||
: null;
|
||||
|
||||
// Preload all subclass features for acquisition from the cache
|
||||
// todo: make feature acquisition async and replace feature helpers for methods
|
||||
await fromUuids(this._source.features.map(f => f.item));
|
||||
|
||||
const foundationFeatures = await getFeaturesHTMLData(this.foundationFeatures);
|
||||
const specializationFeatures = await getFeaturesHTMLData(this.specializationFeatures);
|
||||
const masteryFeatures = await getFeaturesHTMLData(this.masteryFeatures);
|
||||
|
|
|
|||
|
|
@ -28,7 +28,10 @@ export default class DHWeapon extends AttachableItem {
|
|||
equipped: new fields.BooleanField({ initial: false }),
|
||||
|
||||
//SETTINGS
|
||||
secondary: new fields.BooleanField({ initial: false, label: 'DAGGERHEART.ITEMS.Weapon.secondaryWeapon' }),
|
||||
secondary: new fields.BooleanField({
|
||||
initial: false,
|
||||
label: 'DAGGERHEART.ITEMS.Weapon.secondaryWeapon.full'
|
||||
}),
|
||||
burden: new fields.StringField({
|
||||
required: true,
|
||||
choices: CONFIG.DH.GENERAL.burden,
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue