Skip to content

Commit

Permalink
[foundryvtt#1401] Add apply, restore, & revert methods, fix issue wit…
Browse files Browse the repository at this point in the history
…h dropping existing items, localize chosen text
  • Loading branch information
arbron committed Aug 22, 2022
1 parent 399f17f commit 93979e4
Show file tree
Hide file tree
Showing 4 changed files with 68 additions and 5 deletions.
1 change: 1 addition & 0 deletions lang/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -115,6 +115,7 @@
"DND5E.AdvancementItemChoiceHint": "Present the player with a choice of items (such as equipment, features, or spells) that they can choose for their character at one or more levels.",
"DND5E.AdvancementItemChoiceAllowDrops": "Allow Drops",
"DND5E.AdvancementItemChoiceAllowDropsHint": "Should players be able to drop their own choices into this advancement?",
"DND5E.AdvancementItemChoiceChosen": "Chosen: {current} of {max}",
"DND5E.AdvancementItemChoiceConfigDropHint": "Drop Items here to add them to the pool from which a player can choose.",
"DND5E.AdvancementItemChoiceFlowDropHint": "Drop an Item here to choose it.",
"DND5E.AdvancementItemChoiceLevelsHint": "Specify how many choices are allowed at each level.",
Expand Down
66 changes: 64 additions & 2 deletions module/advancement/types/item-choice.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,66 @@ export class ItemChoiceAdvancement extends Advancement {
return Object.values(items).reduce((html, uuid) => html + game.dnd5e.utils._linkForUuid(uuid), "");
}

/* -------------------------------------------- */
/* Application Methods */
/* -------------------------------------------- */

/**
* Locally apply this advancement to the actor.
* @param {number} level Level being advanced.
* @param {object} data Data from the advancement form.
* @param {object} [retainedData={}] Item data grouped by UUID. If present, this data will be used rather than
* fetching new data from the source.
*/
async apply(level, data, retainedData={}) {
const items = [];
const updates = {};
for ( const [uuid, selected] of Object.entries(data) ) {
if ( !selected ) continue;
const item = retainedData[uuid] ? new Item.implementation(retainedData[uuid]) : (await fromUuid(uuid))?.clone();
if ( !item ) continue;
item.data.update({
_id: retainedData[uuid]?._id ?? foundry.utils.randomID(),
"flags.dnd5e.sourceId": uuid,
"flags.dnd5e.advancementOrigin": `${this.item.id}.${this.id}`
});
items.push(item.toObject());
// TODO: Trigger any additional advancement steps for added items
updates[item.id] = uuid;
}
this.actor.data.update({items});
this.updateSource({[`value.${level}`]: updates});
}

/* -------------------------------------------- */

/** @inheritdoc */
restore(level, data) {
const updates = {};
for ( const item of data.items ) {
this.actor.data.update({items: [item]});
// TODO: Restore any additional advancement data here
updates[item._id] = item.flags.dnd5e.sourceId;
}
this.updateSource({[`value.${level}`]: updates});
}

/* -------------------------------------------- */

/** @inheritdoc */
reverse(level) {
const items = [];
for ( const id of Object.keys(this.data.value[level] ?? {}) ) {
const item = this.actor.items.get(id);
if ( item ) items.push(item.toObject());
this.actor.items.delete(id);
// TODO: Ensure any advancement data attached to these items is properly reversed
// and store any advancement data for these items in case they need to be restored
}
this.updateSource({[`value.-=${level}`]: null });
return { items };
}

}


Expand Down Expand Up @@ -227,7 +287,6 @@ export class ItemChoiceFlow extends AdvancementFlow {

if ( data.type !== "Item" ) return false;
const item = await Item.implementation.fromDropData(data);
item.dropped = true;

// If the item is already been marked as selected, no need to go further
if ( this.selected.has(item.uuid) ) return false;
Expand All @@ -238,7 +297,10 @@ export class ItemChoiceFlow extends AdvancementFlow {
this.selected.add(item.uuid);

// If the item doesn't already exist in the pool, add it
if ( !this.pool.find(i => i.uuid === item.uuid) ) this.dropped.push(item);
if ( !this.pool.find(i => i.uuid === item.uuid) ) {
this.dropped.push(item);
item.dropped = true;
}

this.render();
}
Expand Down
1 change: 0 additions & 1 deletion templates/advancement/item-choice-config.html
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
<form autocomplete="off">
{{log this}}
<div class="left-column">
{{> "systems/dnd5e/templates/advancement/parts/advancement-controls.html"}}
<div class="form-group">
Expand Down
5 changes: 3 additions & 2 deletions templates/advancement/item-choice-flow.html
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,10 @@ <h3>{{{title}}}</h3>
<p>{{advancement.data.configuration.hint}}</p>
{{/if}}

<h4 class="form-header">Chosen: <span class="current">{{choices.current}}</span> of {{choices.max}}</h4>
<h4 class="form-header">
{{localize "DND5E.AdvancementItemChoiceChosen" current=choices.current max=choices.max}}
</h4>

{{log this}}
<div class="drop-target">
{{#each items}}
<div class="item-name flexrow">
Expand Down

0 comments on commit 93979e4

Please sign in to comment.