conversion macro

@max.pat did you have a macro or script which could change the old classFeatures data into advancements on their items?
C
Calego731d ago
I had one a long time ago, let me try to dig it up it definitely will need updating
UU
Unknown User731d ago
C
Calego731d ago
gotchya. well if you happen upon one or anyone interested in making one, send em our way will ya?
UU
Unknown User731d ago
C
Calego731d ago
this is what I had a long time ago (but definitely needs some updating):
bad code dont use, look below
bad code dont use, look below
I used this with updateAll cc @kandashi ^ for if you are interested 😉 I won't have time till this weekend probabaly to iron this out, but will do so when I can @Zhell you might be interested here too
UU
Unknown User731d ago
C
Calego731d ago
I'm thinking that since the class features work is already done, we can use that format to populate class items and subclass items Basically not directly parsing the JSON you have here Macro runnable snippet which will take an existing compendium with Class Items, and update that compendium's items with advancements as defined in the deprecated CONFIG.DND5E.classFeatures (useful for some modules which overrode or extended this).
const PACK_NAME = 'world.blank-class-items';
/* Update All Class Items in the Compendium per legacy CONFIG.DND5E.classFeatures */
/* v0.3 */
const pack = game.packs.get(PACK_NAME);

if (!pack) {
ui.notifications.error('No pack by that name');
return;
};

const docs = await pack.getDocuments();

for (let item of docs) {
const className = item.name.slugify({strict: true});
const clsConfig = CONFIG.DND5E.classFeatures[className];
if (!clsConfig) continue;

const advancements = Object.entries(clsConfig.features).map(([level, items]) => {
return {
classRestriction: "",
level,
icon: "",
type: 'ItemGrant',
title: "Features",
configuration: { items },
value: {},
_id: foundry.utils.randomID(),
}
});

// add hitpoints advancement because this is a class
advancements.push({
classRestriction: "",
type: "HitPoints",
icon: "",
title: "",
configuration: {},
value: {},
_id: foundry.utils.randomID(),
});

await item.update({
'data.advancement': advancements
});
}

pack.render(true);
ui.notifications.notify('Complete');
const PACK_NAME = 'world.blank-class-items';
/* Update All Class Items in the Compendium per legacy CONFIG.DND5E.classFeatures */
/* v0.3 */
const pack = game.packs.get(PACK_NAME);

if (!pack) {
ui.notifications.error('No pack by that name');
return;
};

const docs = await pack.getDocuments();

for (let item of docs) {
const className = item.name.slugify({strict: true});
const clsConfig = CONFIG.DND5E.classFeatures[className];
if (!clsConfig) continue;

const advancements = Object.entries(clsConfig.features).map(([level, items]) => {
return {
classRestriction: "",
level,
icon: "",
type: 'ItemGrant',
title: "Features",
configuration: { items },
value: {},
_id: foundry.utils.randomID(),
}
});

// add hitpoints advancement because this is a class
advancements.push({
classRestriction: "",
type: "HitPoints",
icon: "",
title: "",
configuration: {},
value: {},
_id: foundry.utils.randomID(),
});

await item.update({
'data.advancement': advancements
});
}

pack.render(true);
ui.notifications.notify('Complete');
A class compendium migration script for your guys' perusal and testing. Gonna work on one that creates a compendium for subclasses next as I have time. Then one which attempts to migrate an existing actor.
UU
Unknown User731d ago
C
Calego731d ago
ohhhh nooooo did we break this with the deprecation warning?? If you have this locally, can you test something for me? In config.js in the 5e repo files, change the classFeatures block to be this
/**
* Character features automatically granted by classes & subclasses at certain levels.
* @type {object}
*/
Object.defineProperty(DND5E, "classFeatures", {
_classFeatures: ClassFeatures,
get() {
console.warn(
"The classFeatures object is deprecated. Please use the new Advancement API to configure class features.");
return this._classFeatures;
},
set(newClassFeatures) {
this._classFeatures = newClassFeatures;
},
configurable: true,
enumerable: true
});
/**
* Character features automatically granted by classes & subclasses at certain levels.
* @type {object}
*/
Object.defineProperty(DND5E, "classFeatures", {
_classFeatures: ClassFeatures,
get() {
console.warn(
"The classFeatures object is deprecated. Please use the new Advancement API to configure class features.");
return this._classFeatures;
},
set(newClassFeatures) {
this._classFeatures = newClassFeatures;
},
configurable: true,
enumerable: true
});
UU
Unknown User731d ago
C
Calego731d ago
that would be because they're setting something nested within the object I guess. You look to be replacing the object itself (which should still be supported and hopefully my snippet will allow that)
UU
Unknown User731d ago
C
Calego731d ago
that looks like it works just based on my rudimentary testing
UU
Unknown User731d ago
C
Calego731d ago
wtf...
UU
Unknown User731d ago
C
Calego731d ago
😬
UU
Unknown User731d ago
C
Calego731d ago
it's not good that I broke the other by fixing the one
UU
Unknown User731d ago
C
Calego731d ago
yeah what I sent above is definitely not right its close but this is some black magic that's beyond me...
C
Calego731d ago
GitLab
1.6.0 allow replacing class features entirely (#1503) · Issues · Fo...
Modules like custom classes have provided GMs a framework to replace the CONFIG.DND5E.classFeatures object entirely. The deprecation warning added in 1.6.0 broke this...
C
Calego731d ago
Macro runnable snippet which will take an existing compendium and create subclasses in that compendium with advancements as defined in the deprecated CONFIG.DND5E.classFeatures (useful for some modules which overrode or extended this, in theory). Will not create duplicates (determined by name). Optionally allows creation of "empty" subclasses which have no features defined (core 5e lists a lot of RAW subclasses without features).
// the compendium id which should have the subclasses added to it
const PACK_NAME = 'world.custom-subclasses';

// the core system includes subclasses without features defined, should these be created as subclasses?
const INCLUDE_EMPTY_SUBCLASSES = false;

/* Create Subclass Items that are missing (based on name matching) in the Compendium per legacy CONFIG.DND5E.classFeatures */
/* v0.1 */
const pack = game.packs.get(PACK_NAME);

if (!pack) {
ui.notifications.error('No pack by that name');
return;
};

const itemData = Object.entries(CONFIG.DND5E.classFeatures).map(([classIdentifier, { subclasses }]) => {
const subclassItemData = Object.entries(subclasses).map(([subclassIdentifier, { label, features, source }]) => {
if (!INCLUDE_EMPTY_SUBCLASSES && (!features || foundry.utils.isObjectEmpty(features))) return;

const advancements = (!features || foundry.utils.isObjectEmpty(features)) ? [] : Object.entries(features).map(([level, items]) => {
return {
classRestriction: "",
level,
icon: "",
type: 'ItemGrant',
title: "Features",
configuration: { items },
value: {},
_id: foundry.utils.randomID(),
}
});

return {
data: {
advancement: advancements,
identifier: subclassIdentifier,
classIdentifier,
source,
},
name: label,
type: 'subclass'
}
});

return subclassItemData;

}).flat().filter(Boolean).filter(({name}) => !pack.index.getName(name));

console.log("Creating Items:", itemData);
await Item.implementation.create(itemData, { pack: PACK_NAME });

pack.render(true);
ui.notifications.notify('Complete');
// the compendium id which should have the subclasses added to it
const PACK_NAME = 'world.custom-subclasses';

// the core system includes subclasses without features defined, should these be created as subclasses?
const INCLUDE_EMPTY_SUBCLASSES = false;

/* Create Subclass Items that are missing (based on name matching) in the Compendium per legacy CONFIG.DND5E.classFeatures */
/* v0.1 */
const pack = game.packs.get(PACK_NAME);

if (!pack) {
ui.notifications.error('No pack by that name');
return;
};

const itemData = Object.entries(CONFIG.DND5E.classFeatures).map(([classIdentifier, { subclasses }]) => {
const subclassItemData = Object.entries(subclasses).map(([subclassIdentifier, { label, features, source }]) => {
if (!INCLUDE_EMPTY_SUBCLASSES && (!features || foundry.utils.isObjectEmpty(features))) return;

const advancements = (!features || foundry.utils.isObjectEmpty(features)) ? [] : Object.entries(features).map(([level, items]) => {
return {
classRestriction: "",
level,
icon: "",
type: 'ItemGrant',
title: "Features",
configuration: { items },
value: {},
_id: foundry.utils.randomID(),
}
});

return {
data: {
advancement: advancements,
identifier: subclassIdentifier,
classIdentifier,
source,
},
name: label,
type: 'subclass'
}
});

return subclassItemData;

}).flat().filter(Boolean).filter(({name}) => !pack.index.getName(name));

console.log("Creating Items:", itemData);
await Item.implementation.create(itemData, { pack: PACK_NAME });

pack.render(true);
ui.notifications.notify('Complete');
UU
Unknown User731d ago
C
Calego731d ago
OK THIS ONES GNARLY. This is 0.1 for a macro script which will migrate an actor to use class advancement which doesn't currently. It makes some assumptions: 1. The class item being used has a core.sourceId flag (happens when you drag/drop from a compendium/world item). 2. That original class item has been updated to have advancements. 3. Those advancements reference the same items as were manually added to the actor before. https://gist.github.com/akrigline/170159bf376969b69c25a62f97398982#file-migrate-actor-js migrate-actor.js in the gist I was able to use this on a 1.5.x "Starter Hero" (Quillathe) to introduce advancements to them in 1.6.x Haven't gotten my head wrapped around adding a subclass item automatically yet and am too tired to try that tonight, but it's on the todo for this bad boy. @unsoluble this one might interest you, try at your own risk 😛 Obviously not ready for sharing at large but you expressed interest on the mothership so now I'm pulling you in here 🙂
UU
Unknown User731d ago
C
Calego731d ago
can always make a duplicate and run it on that, i do that sort of thing a lot 😛
UU
Unknown User731d ago
C
Calego730d ago
Right Well, kinda. It will try to configure the actor as though it has been getting advancements the whole time getting the class item that was added to the actor originally. It nukes any hp advancements because idk how I could figure out that info to backfill. But it will look at the item grants and try to match up existing items on the actor with items they should have been granted if they had gone through the advancement flows. This does not back fill items "missing" from the advancement, it assumes more or less that the actor is currently configured well, but wants to use advancement going forwards. For any level lower than the current level of that class, it turns the item grant advancement into an optional one; then updates items with the flag to make it appear they are from an advancement. @alaustin this channel might be of interest to you in your quest to migrate your data
UU
Unknown User716d ago
C
Calego716d ago
yeah let me put some snippets up on the repo
C
Calego716d ago
@max.pat https://gitlab.com/foundrynet/dnd5e/-/snippets/2313873 https://gitlab.com/foundrynet/dnd5e/-/snippets/2313875 all yours :P. I'll try to post something about them in the mothership today, but i've not been good about self-imposed timers lately.
GitLab
1.6.1 Subclass Compendium Item Creation ($2313873) · Snippets · Fou...
An implementation of the Dungeons & Dragons 5th Edition game system for Foundry Virtual Tabletop (http://foundryvtt.com). This work is permitted under the Open...
GitLab
1.6.1 Class Compendium Migration ($2313875) · Snippets · Foundry Ne...
An implementation of the Dungeons & Dragons 5th Edition game system for Foundry Virtual Tabletop (http://foundryvtt.com). This work is permitted under the Open...
UU
Unknown User716d ago
LTL
Leo The League Lion716d ago
@max.pat gave vote LeaguePoints™ to @calego (#1 • 1495)
Z
Zhell715d ago
I dunno if there is any interest but I made a conversion macro of my own of sorts using regex that takes any subclass item and creates the features and advancement as long as it's written in the right formatting, i.e., in the likeness of dndbeyond:
<p>subclass description goes here</p>
<h2>feature name</h2>
<p><em>xth-level subclassName feature</em></p>
<p>feature description...</p>
<h2> etc etc
<p>subclass description goes here</p>
<h2>feature name</h2>
<p><em>xth-level subclassName feature</em></p>
<p>feature description...</p>
<h2> etc etc
It sets up the feature's description.value, the advancement in the subclass, the requirement on the features and slaps them all in a compendium.
UU
Unknown User682d ago
Z
Zhell682d ago
oh shoot, lemme see if I still have it
Z
Zhell682d ago
I think this was it, I got a few.
UU
Unknown User682d ago
LTL
Leo The League Lion682d ago
@max.pat gave vote LeaguePoints™ to @Zhell (#200 • 3)
Want results from more Discord servers?
Add your server
More Posts
AC calc changesI do not believe the data for AC actually changed, only the way it is calculated. evidence: no chang1.6.0 Custom Sheet ChangesLooking at the changes made which are breaking for custom sheets. Gonna make a thread for this.1.6.0 testingCommunity Testing Requests: For those of you interested in helping to QA this branch, I'll put togeHook documentationdnd5e Hook Documentation: https://gitlab.com/foundrynet/dnd5e/-/wikis/HooksTyphonJS Runtime Library v0.0.9 - Release CandidateAlrighty! The TyphonJS Runtime Library (TRL) v0.0.9 is out... In the last 2 weeks+ I have done massi1.6.0 - 82%@dnd5e - **No action Required** The 1.6.0 milestone is at 82% completion https://gitlab.com/foundryadvancement consumptionnow that I brought that up on #progress-reports @calego , could I maybe pester you later for some adAlternative Alignment System D&D5eWow, that is a really powerful way to codify alignment. I like it! Do you have any ideas as to how iconsumables chat data@Zhell > So that's odd. How come consumables work different and all other item types get a non-funcilthid stop dragActually, would it be possible to modify the core function that allows people to click and drag toke1.6.x mid-milestone update@dnd5e - **No Action Required** Milestone 1.6.0 is 69% Complete (_nice_) <https://gitlab.com/foundPlugin ContributorsI'm very proud to be the maintainer of a module (Export Sheet to PDF) that is getting many, many conmore-hooks-itemroll-hooksFor those of you interested in such things, I have hacked together a way to inject hooks into the mipreHooks5eJSON.stringify jankI discovered that the problem is JSON.stringify, not parselayersTIL about CSS Layers. https://developer.mozilla.org/en-US/docs/Web/CSS/@layer ```css @layer utilitiHitDice hooks MRI just added my first merge request 😄 <https://gitlab.com/foundrynet/dnd5e/-/merge_requests/495>advantage shennaneginsdevmode extension brainstormhttps://github.com/mdn/webextensions-examples/tree/master/devtools-panelsSaving Functions as module settings@wasp I remember you asked about saving functions as settings (which quickly turned into stringifyin