mirror of
https://github.com/Foundryborne/daggerheart.git
synced 2026-06-06 04:44:16 +02:00
Merge branch 'main' into feature/total-reroll
This commit is contained in:
commit
06c70b7e58
26 changed files with 270 additions and 176 deletions
|
|
@ -175,14 +175,14 @@ export default class D20RollDialog extends HandlebarsApplicationMixin(Applicatio
|
|||
this.disadvantage = advantage === -1;
|
||||
|
||||
this.config.roll.advantage = this.config.roll.advantage === advantage ? 0 : advantage;
|
||||
if (this.config.roll.advantage === 0) return this.render();
|
||||
|
||||
if (this.config.roll.advantage === 1 && this.config.data.rules.roll.defaultAdvantageDice) {
|
||||
const faces = Number.parseInt(this.config.data.rules.roll.defaultAdvantageDice);
|
||||
this.roll.advantageFaces = Number.isNaN(faces) ? this.roll.advantageFaces : faces;
|
||||
} else if (this.config.roll.advantage === -1 && this.config.data.rules.roll.defaultDisadvantageDice) {
|
||||
const faces = Number.parseInt(this.config.data.rules.roll.defaultDisadvantageDice);
|
||||
this.roll.advantageFaces = Number.isNaN(faces) ? this.roll.advantageFaces : faces;
|
||||
}
|
||||
const defaultFaces =
|
||||
this.config.roll.advantage === 1
|
||||
? this.config.data.rules.roll.defaultAdvantageDice
|
||||
: this.config.data.rules.roll.defaultDisadvantageDice;
|
||||
const faces = Number.parseInt(defaultFaces);
|
||||
this.roll.advantageFaces = Number.isNaN(faces) ? this.roll.advantageFaces : faces;
|
||||
|
||||
this.render();
|
||||
}
|
||||
|
|
|
|||
|
|
@ -204,7 +204,7 @@ export default class DHActionBaseConfig extends DaggerheartSheet(ApplicationV2)
|
|||
};
|
||||
}
|
||||
|
||||
if (this.action.parent.metadata?.isQuantifiable) {
|
||||
if (this.action.parent.metadata.isInventoryItem) {
|
||||
options.quantity = {
|
||||
label: 'DAGGERHEART.GENERAL.itemQuantity',
|
||||
group: 'Global'
|
||||
|
|
|
|||
|
|
@ -175,6 +175,7 @@ export default class DhActiveEffectConfig extends foundry.applications.sheets.Ac
|
|||
const partContext = await super._preparePartContext(partId, context);
|
||||
switch (partId) {
|
||||
case 'details':
|
||||
partContext.isItemEffect = partContext.isItemEffect || this.options.isSetting;
|
||||
const useGeneric = game.settings.get(
|
||||
CONFIG.DH.id,
|
||||
CONFIG.DH.SETTINGS.gameSettings.appearance
|
||||
|
|
|
|||
|
|
@ -184,6 +184,9 @@ export default class CharacterSheet extends DHBaseActorSheet {
|
|||
for (const input of form.querySelectorAll('input:not([type=search]), .editor.prosemirror')) {
|
||||
input.disabled = disabled;
|
||||
}
|
||||
for (const element of form.querySelectorAll('.input[contenteditable]')) {
|
||||
element.classList.toggle('disabled', disabled);
|
||||
}
|
||||
}
|
||||
|
||||
/** @inheritDoc */
|
||||
|
|
@ -368,7 +371,7 @@ export default class CharacterSheet extends DHBaseActorSheet {
|
|||
const doc = getDocFromElementSync(target);
|
||||
return doc?.isOwner && !isItemWizardManaged(doc);
|
||||
},
|
||||
callback: async (target, event) => {
|
||||
onClick: async (event, target) => {
|
||||
const doc = await getDocFromElement(target);
|
||||
if (event.shiftKey) return doc.delete();
|
||||
else return doc.deleteDialog();
|
||||
|
|
@ -393,7 +396,7 @@ export default class CharacterSheet extends DHBaseActorSheet {
|
|||
const doc = getDocFromElementSync(target);
|
||||
return doc?.isOwner && doc.system.inVault;
|
||||
},
|
||||
callback: async target => {
|
||||
onClick: async (_, target) => {
|
||||
const doc = await getDocFromElement(target);
|
||||
const actorLoadout = doc.actor.system.loadoutSlot;
|
||||
if (actorLoadout.available) return doc.update({ 'system.inVault': false });
|
||||
|
|
@ -407,7 +410,7 @@ export default class CharacterSheet extends DHBaseActorSheet {
|
|||
const doc = getDocFromElementSync(target);
|
||||
return doc?.isOwner && doc.system.inVault;
|
||||
},
|
||||
callback: async (target, event) => {
|
||||
onClick: async (event, target) => {
|
||||
const doc = await getDocFromElement(target);
|
||||
const actorLoadout = doc.actor.system.loadoutSlot;
|
||||
if (!actorLoadout.available) {
|
||||
|
|
@ -446,7 +449,7 @@ export default class CharacterSheet extends DHBaseActorSheet {
|
|||
const doc = getDocFromElementSync(target);
|
||||
return doc?.isOwner && !doc.system.inVault;
|
||||
},
|
||||
callback: async target => (await getDocFromElement(target)).update({ 'system.inVault': true })
|
||||
onClick: async (_, target) => (await getDocFromElement(target)).update({ 'system.inVault': true })
|
||||
}
|
||||
].map(option => ({
|
||||
...option,
|
||||
|
|
@ -472,7 +475,7 @@ export default class CharacterSheet extends DHBaseActorSheet {
|
|||
const doc = getDocFromElementSync(target);
|
||||
return doc.isOwner && doc && !doc.system.equipped;
|
||||
},
|
||||
callback: (target, event) => CharacterSheet.#toggleEquipItem.call(this, event, target)
|
||||
onClick: (event, target) => CharacterSheet.#toggleEquipItem.call(this, event, target)
|
||||
},
|
||||
{
|
||||
label: 'unequip',
|
||||
|
|
@ -481,7 +484,7 @@ export default class CharacterSheet extends DHBaseActorSheet {
|
|||
const doc = getDocFromElementSync(target);
|
||||
return doc.isOwner && doc && doc.system.equipped;
|
||||
},
|
||||
callback: (target, event) => CharacterSheet.#toggleEquipItem.call(this, event, target)
|
||||
onClick: (event, target) => CharacterSheet.#toggleEquipItem.call(this, event, target)
|
||||
}
|
||||
].map(option => ({
|
||||
...option,
|
||||
|
|
|
|||
|
|
@ -424,7 +424,7 @@ export default function DHApplicationMixin(Base) {
|
|||
const target = element.closest('[data-item-uuid]');
|
||||
return !target.dataset.disabled && target.dataset.itemType !== 'beastform';
|
||||
},
|
||||
callback: async target => (await getDocFromElement(target)).update({ disabled: true })
|
||||
onClick: async (_, target) => (await getDocFromElement(target)).update({ disabled: true })
|
||||
},
|
||||
{
|
||||
label: 'enableEffect',
|
||||
|
|
@ -433,7 +433,7 @@ export default function DHApplicationMixin(Base) {
|
|||
const target = element.closest('[data-item-uuid]');
|
||||
return target.dataset.disabled && target.dataset.itemType !== 'beastform';
|
||||
},
|
||||
callback: async target => (await getDocFromElement(target)).update({ disabled: false })
|
||||
onClick: async (_, target) => (await getDocFromElement(target)).update({ disabled: false })
|
||||
}
|
||||
].map(option => ({
|
||||
...option,
|
||||
|
|
@ -478,7 +478,9 @@ export default function DHApplicationMixin(Base) {
|
|||
(doc?.isOwner && (!doc?.hasOwnProperty('systemPath') || doc?.inCollection))
|
||||
);
|
||||
},
|
||||
callback: async target => (await getDocFromElement(target)).sheet.render({ force: true })
|
||||
onClick: async (_, target) => {
|
||||
return (await getDocFromElement(target)).sheet.render({ force: true });
|
||||
}
|
||||
}
|
||||
];
|
||||
|
||||
|
|
@ -493,7 +495,7 @@ export default function DHApplicationMixin(Base) {
|
|||
!foundry.utils.isEmpty(doc?.damage?.parts);
|
||||
return doc?.isOwner && hasDamage;
|
||||
},
|
||||
callback: async (target, event) => {
|
||||
onClick: async (event, target) => {
|
||||
const doc = await getDocFromElement(target),
|
||||
action = doc?.system?.attack ?? doc;
|
||||
const config = action.prepareConfig(event);
|
||||
|
|
@ -513,7 +515,7 @@ export default function DHApplicationMixin(Base) {
|
|||
const doc = getDocFromElementSync(target);
|
||||
return doc?.isOwner && !(doc.type === 'domainCard' && doc.system.inVault);
|
||||
},
|
||||
callback: async (target, event) => (await getDocFromElement(target)).use(event)
|
||||
onClick: async (event, target) => (await getDocFromElement(target)).use(event)
|
||||
});
|
||||
}
|
||||
|
||||
|
|
@ -521,7 +523,7 @@ export default function DHApplicationMixin(Base) {
|
|||
options.push({
|
||||
label: 'DAGGERHEART.APPLICATIONS.ContextMenu.sendToChat',
|
||||
icon: 'fa-solid fa-message',
|
||||
callback: async target => (await getDocFromElement(target)).toChat(this.document.uuid)
|
||||
onClick: async (_, target) => (await getDocFromElement(target)).toChat(this.document.uuid)
|
||||
});
|
||||
|
||||
if (deletable)
|
||||
|
|
@ -533,7 +535,7 @@ export default function DHApplicationMixin(Base) {
|
|||
const doc = getDocFromElementSync(target);
|
||||
return doc?.isOwner !== false && target.dataset.itemType !== 'beastform';
|
||||
},
|
||||
callback: async (target, event) => {
|
||||
onClick: async (event, target) => {
|
||||
const doc = await getDocFromElement(target);
|
||||
if (event.shiftKey) return doc.delete();
|
||||
else return doc.deleteDialog();
|
||||
|
|
|
|||
|
|
@ -166,6 +166,15 @@ export default class DHBaseActorSheet extends DHApplicationMixin(ActorSheetV2) {
|
|||
}
|
||||
}
|
||||
|
||||
/** Add support for input content editables */
|
||||
_toggleDisabled(disabled) {
|
||||
super._toggleDisabled(disabled);
|
||||
const form = this.form;
|
||||
for (const element of form.querySelectorAll('.input[contenteditable]')) {
|
||||
element.classList.toggle('disabled', disabled);
|
||||
}
|
||||
}
|
||||
|
||||
/* -------------------------------------------- */
|
||||
/* Context Menu */
|
||||
/* -------------------------------------------- */
|
||||
|
|
|
|||
|
|
@ -126,7 +126,7 @@ export default class DHBaseItemSheet extends DHApplicationMixin(ItemSheetV2) {
|
|||
options.push({
|
||||
name: 'CONTROLS.CommonDelete',
|
||||
icon: '<i class="fa-solid fa-trash"></i>',
|
||||
callback: async target => {
|
||||
onClick: async (_, target) => {
|
||||
const feature = await getDocFromElement(target);
|
||||
if (!feature) return;
|
||||
const confirmed = await foundry.applications.api.DialogV2.confirm({
|
||||
|
|
|
|||
|
|
@ -1,3 +1,4 @@
|
|||
import { getDocFromElement } from '../../helpers/utils.mjs';
|
||||
import { RefreshType, socketEvent } from '../../systemRegistration/socket.mjs';
|
||||
|
||||
const { HandlebarsApplicationMixin, ApplicationV2 } = foundry.applications.api;
|
||||
|
|
@ -47,7 +48,8 @@ export class ItemBrowser extends HandlebarsApplicationMixin(ApplicationV2) {
|
|||
expandContent: this.expandContent,
|
||||
resetFilters: this.resetFilters,
|
||||
sortList: this.sortList,
|
||||
openSettings: this.openSettings
|
||||
openSettings: this.openSettings,
|
||||
viewSheet: this.#onViewSheet
|
||||
},
|
||||
position: {
|
||||
left: 100,
|
||||
|
|
@ -306,7 +308,8 @@ export class ItemBrowser extends HandlebarsApplicationMixin(ApplicationV2) {
|
|||
{
|
||||
items: this.items,
|
||||
menu: this.selectedMenu,
|
||||
formatLabel: this.formatLabel
|
||||
formatLabel: this.formatLabel,
|
||||
viewSheet: this.items[0] instanceof Actor
|
||||
}
|
||||
);
|
||||
|
||||
|
|
@ -568,6 +571,11 @@ export class ItemBrowser extends HandlebarsApplicationMixin(ApplicationV2) {
|
|||
}
|
||||
}
|
||||
|
||||
static async #onViewSheet(_, target) {
|
||||
const document = await getDocFromElement(target);
|
||||
document?.sheet?.render(true);
|
||||
}
|
||||
|
||||
_createDragProcess() {
|
||||
new foundry.applications.ux.DragDrop.implementation({
|
||||
dragSelector: '.item-container',
|
||||
|
|
@ -606,7 +614,16 @@ export class ItemBrowser extends HandlebarsApplicationMixin(ApplicationV2) {
|
|||
items: {
|
||||
folder: 'equipments',
|
||||
render: {
|
||||
noFolder: true
|
||||
folders: [
|
||||
'equipments',
|
||||
'ancestries',
|
||||
'classes',
|
||||
'subclasses',
|
||||
'domains',
|
||||
'communities',
|
||||
'beastforms'
|
||||
// excluded: features
|
||||
]
|
||||
}
|
||||
},
|
||||
compendium: {}
|
||||
|
|
|
|||
|
|
@ -148,10 +148,14 @@ export default class DHBaseAction extends ActionMixin(foundry.abstract.DataModel
|
|||
: null;
|
||||
}
|
||||
|
||||
/** Returns true if the action is usable */
|
||||
/**
|
||||
* Returns true if the action is usable.
|
||||
* An action is usable on any actor type. For example, an adversary might have a base attack action.
|
||||
*/
|
||||
get usable() {
|
||||
const actor = this.actor;
|
||||
return this.isOwner && actor?.type === 'character';
|
||||
const pack = actor?.pack ? game.packs.get(actor.pack) : null;
|
||||
return !pack?.locked && this.isOwner;
|
||||
}
|
||||
|
||||
static getRollType(parent) {
|
||||
|
|
|
|||
|
|
@ -103,7 +103,7 @@ export default class CostField extends fields.ArrayField {
|
|||
static calcCosts(costs) {
|
||||
const resources = CostField.getResources.call(this, costs);
|
||||
let filteredCosts = costs;
|
||||
if (this.parent?.metadata.isQuantifiable && this.parent.consumeOnUse === false) {
|
||||
if (this.parent?.isInventoryItem && this.parent.consumeOnUse === false) {
|
||||
filteredCosts = filteredCosts.filter(c => c.key !== 'quantity');
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -150,14 +150,22 @@ export default class DualityRoll extends D20Roll {
|
|||
}
|
||||
|
||||
applyAdvantage() {
|
||||
if (this.hasAdvantage || this.hasDisadvantage) {
|
||||
const dieFaces = this.advantageFaces,
|
||||
advDie = new foundry.dice.terms.Die({ faces: dieFaces, number: this.advantageNumber });
|
||||
if (this.advantageNumber > 1) advDie.modifiers = ['kh'];
|
||||
this.terms.push(
|
||||
new foundry.dice.terms.OperatorTerm({ operator: this.hasDisadvantage ? '-' : '+' }),
|
||||
advDie
|
||||
);
|
||||
const advDieClass = this.hasAdvantage
|
||||
? game.system.api.dice.diceTypes.AdvantageDie
|
||||
: this.hasDisadvantage
|
||||
? game.system.api.dice.diceTypes.DisadvantageDie
|
||||
: null;
|
||||
if (advDieClass) {
|
||||
const advDie = new advDieClass({ faces: this.advantageFaces, number: this.advantageNumber });
|
||||
if (this.terms.length < 4) {
|
||||
if (this.advantageNumber > 1) advDie.modifiers = ['kh'];
|
||||
this.terms.push(
|
||||
new foundry.dice.terms.OperatorTerm({ operator: this.hasDisadvantage ? '-' : '+' }),
|
||||
advDie
|
||||
);
|
||||
} else {
|
||||
this.terms[4] = advDie;
|
||||
}
|
||||
}
|
||||
if (this.rallyFaces)
|
||||
this.terms.push(
|
||||
|
|
|
|||
|
|
@ -73,8 +73,10 @@ export default class DHItem extends foundry.documents.Item {
|
|||
/** Returns true if the item can be used */
|
||||
get usable() {
|
||||
const actor = this.actor;
|
||||
const actionsList = this.system.actionsList;
|
||||
return this.isOwner && actor?.type === 'character' && (actionsList?.size || actionsList?.length);
|
||||
const pack = actor?.pack ? game.packs.get(actor.pack) : null;
|
||||
const hasActions = this.system.actionsList?.size || this.system.actionsList?.length;
|
||||
const isValidType = actor?.type === 'character' || this.type === 'feature';
|
||||
return !pack?.locked && this.isOwner && isValidType && hasActions;
|
||||
}
|
||||
|
||||
/** @inheritdoc */
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue