Skip to content

Commit

Permalink
Merge pull request #1 from mattstjean/v9-compatibility
Browse files Browse the repository at this point in the history
V9 compatibility
  • Loading branch information
mattstjean authored Apr 29, 2022
2 parents 69ea0a9 + 775887e commit 10f4131
Show file tree
Hide file tree
Showing 5 changed files with 59 additions and 68 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
# CHANGELOG

## [2.4.0] 2022-04-29

- Add compatibility for Foundry v9 (MattStJean)

## [2.3.0] 2021-01-16

### CHANGED
Expand Down
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@ Confirmed compatibility with Tidy5e Sheet, Alt5e Sheet, and Better Rolls for 5e.

Makes use of libWrapper to reduce likelihood of conflicts. Installing libWrapper is not required to make use of this module.

Updated to be compatible with Foundry v9.

## License

Licensed under the GPLv3 License (see [LICENSE](LICENSE)).
86 changes: 30 additions & 56 deletions lib/libWrapper/shim.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// SPDX-License-Identifier: LGPL-3.0-or-later
// SPDX-License-Identifier: MIT
// Copyright © 2021 fvtt-lib-wrapper Rui Pinheiro


Expand All @@ -7,6 +7,11 @@
// A shim for the libWrapper library
export let libWrapper = undefined;

export const VERSIONS = [1,12,1];
export const TGT_SPLIT_RE = new RegExp("([^.[]+|\\[('([^'\\\\]|\\\\.)+?'|\"([^\"\\\\]|\\\\.)+?\")\\])", 'g');
export const TGT_CLEANUP_RE = new RegExp("(^\\['|'\\]$|^\\[\"|\"\\]$)", 'g');

// Main shim code
Hooks.once('init', () => {
// Check if the real module is already loaded - if so, use it
if(globalThis.libWrapper && !(globalThis.libWrapper.is_fallback ?? true)) {
Expand All @@ -18,14 +23,26 @@ Hooks.once('init', () => {
libWrapper = class {
static get is_fallback() { return true };

static register(module, target, fn, type="MIXED") {
static get WRAPPER() { return 'WRAPPER' };
static get MIXED() { return 'MIXED' };
static get OVERRIDE() { return 'OVERRIDE' };

static register(package_id, target, fn, type="MIXED", {chain=undefined, bind=[]}={}) {
const is_setter = target.endsWith('#set');
target = !is_setter ? target : target.slice(0, -4);
const split = target.split('.');
const fn_name = split.pop();
const split = target.match(TGT_SPLIT_RE).map((x)=>x.replace(/\\(.)/g, '$1').replace(TGT_CLEANUP_RE,''));
const root_nm = split.splice(0,1)[0];
const _eval = eval; // The browser doesn't expose all global variables (e.g. 'Game') inside globalThis, but it does to an eval. We copy it to a variable to have it run in global scope.
const obj = split.reduce((x,y)=>x[y], globalThis[root_nm] ?? _eval(root_nm));

let obj, fn_name;
if(split.length == 0) {
obj = globalThis;
fn_name = root_nm;
}
else {
const _eval = eval;
fn_name = split.pop();
obj = split.reduce((x,y)=>x[y], globalThis[root_nm] ?? _eval(root_nm));
}

let iObj = obj;
let descriptor = null;
Expand All @@ -34,10 +51,13 @@ Hooks.once('init', () => {
if(descriptor) break;
iObj = Object.getPrototypeOf(iObj);
}
if(!descriptor) throw `libWrapper Shim: '${target}' does not exist or could not be found.`;
if(!descriptor || descriptor?.configurable === false) throw new Error(`libWrapper Shim: '${target}' does not exist, could not be found, or has a non-configurable descriptor.`);

let original = null;
const wrapper = (type == 'OVERRIDE') ? function() { return fn.call(this, ...arguments); } : function() { return fn.call(this, original.bind(this), ...arguments); }
const wrapper = (chain ?? (type.toUpperCase?.() != 'OVERRIDE' && type != 3)) ?
function(...args) { return fn.call(this, original.bind(this), ...bind, ...args); } :
function(...args) { return fn.call(this, ...bind, ...args); }
;

if(!is_setter) {
if(descriptor.value) {
Expand All @@ -50,7 +70,7 @@ Hooks.once('init', () => {
}
}
else {
if(!descriptor.set) throw `libWrapper Shim: '${target}' does not have a setter`;
if(!descriptor.set) throw new Error(`libWrapper Shim: '${target}' does not have a setter`);
original = descriptor.set;
descriptor.set = wrapper;
}
Expand All @@ -59,50 +79,4 @@ Hooks.once('init', () => {
Object.defineProperty(obj, fn_name, descriptor);
}
}

//************** USER CUSTOMIZABLE:
// Whether to warn GM that the fallback is being used
const WARN_FALLBACK = false;

// Set up the ready hook that shows the "libWrapper not installed" warning dialog
if(WARN_FALLBACK) {
//************** USER CUSTOMIZABLE:
// Module ID - by default attempts to auto-detect, but you might want to hardcode your module ID here to avoid potential auto-detect issues
const MODULE_ID = ((import.meta?.url ?? Error().stack)?.match(/(?<=\/)modules\/.+(?=\/)/i)??[])[0]?.split('/')?.find(n => n && game.modules.has(n));
if(!MODULE_ID) {
console.error("libWrapper Shim: Could not auto-detect module ID. The libWrapper fallback warning dialog will be disabled.");
return;
}

Hooks.once('ready', () => {
// Module title
const MODULE_TITLE = game.modules.get(MODULE_ID).data.title;

//************** USER CUSTOMIZABLE:
// Title and message for the dialog shown when the real libWrapper is not installed.
const FALLBACK_MESSAGE_TITLE = MODULE_TITLE;
const FALLBACK_MESSAGE = `
<p><b>'${MODULE_TITLE}' depends on the 'libWrapper' module, which is not present.</b></p>
<p>A fallback implementation will be used, which increases the chance of compatibility issues with other modules.</p>
<small><p>'libWrapper' is a library which provides module developers with a simple way to modify core Foundry VTT code, while reducing the likelihood of conflict with other modules.</p>
<p>You can install it from the "Add-on Modules" tab in the <a href="javascript:game.shutDown()">Foundry VTT Setup</a>, from the <a href="https://foundryvtt.com/packages/lib-wrapper">Foundry VTT package repository</a>, or from <a href="https://github.com/ruipin/fvtt-lib-wrapper/">libWrapper's Github page</a>.</p></small>
`;

// Settings key used for the "Don't remind me again" setting
const DONT_REMIND_AGAIN_KEY = "libwrapper-dont-remind-again";

// Dialog code
console.warn(`${MODULE_TITLE}: libWrapper not present, using fallback implementation.`);
game.settings.register(MODULE_ID, DONT_REMIND_AGAIN_KEY, { name: '', default: false, type: Boolean, scope: 'world', config: false });
if(game.user.isGM && !game.settings.get(MODULE_ID, DONT_REMIND_AGAIN_KEY)) {
new Dialog({
title: FALLBACK_MESSAGE_TITLE,
content: FALLBACK_MESSAGE, buttons: {
ok: { icon: '<i class="fas fa-check"></i>', label: 'Understood' },
dont_remind: { icon: '<i class="fas fa-times"></i>', label: "Don't remind me again", callback: () => game.settings.set(MODULE_ID, DONT_REMIND_AGAIN_KEY, true) }
}
}).render(true);
}
});
}
});
});
31 changes: 21 additions & 10 deletions module.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,20 +5,31 @@
"systems": [
"dnd5e"
],
"version": "2.3.0",
"author": "Cole Schultz (cole#9640)",
"version": "2.4.0",
"authors": [
{
"name": "Cole Schultz",
"url": "https://github.com/schultzcole",
"discord": "cole#9640"
},
{
"name": "Matt St Jean",
"url": "https://github.com/mattstjean",
"discord": "maatttt#9864"
}
],
"esmodules": [
"skl-customization.js"
],
"styles": [
"skl-cust-styles.css"
],
"minimumCoreVersion": "0.6.2",
"compatibleCoreVersion": "0.7.9",
"url": "https://github.com/schultzcole/FVTT-Skill-Customization-5e",
"manifest": "https://raw.githubusercontent.com/schultzcole/FVTT-Skill-Customization-5e/master/module.json",
"download": "https://github.com/schultzcole/FVTT-Skill-Customization-5e/archive/2.3.0.zip",
"license": "https://github.com/schultzcole/FVTT-Skill-Customization-5e/blob/2.3.0/LICENSE",
"readme": "https://github.com/schultzcole/FVTT-Skill-Customization-5e/blob/2.3.0/README.md",
"changelog": "https://github.com/schultzcole/FVTT-Skill-Customization-5e/blob/2.3.0/CHANGELOG.md"
"minimumCoreVersion": "9.235",
"compatibleCoreVersion": "9.255",
"url": "https://github.com/mattstjean/FVTT-Skill-Customization-5e",
"manifest": "https://raw.githubusercontent.com/mattstjean/FVTT-Skill-Customization-5e/master/module.json",
"download": "https://github.com/mattstjean/FVTT-Skill-Customization-5e/archive/2.4.0.zip",
"license": "https://github.com/mattstjean/FVTT-Skill-Customization-5e/blob/2.4.0/LICENSE",
"readme": "https://github.com/mattstjean/FVTT-Skill-Customization-5e/blob/2.4.0/README.md",
"changelog": "https://github.com/mattstjean/FVTT-Skill-Customization-5e/blob/2.4.0/CHANGELOG.md"
}
4 changes: 2 additions & 2 deletions skl-customization.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ Hooks.once("setup", () => {
Hooks.on("renderActorSheet", injectActorSheet);

function patchActor5ePrepareData() {
libWrapper.register(MODULE_NAME, "CONFIG.Actor.entityClass.prototype.prepareData", function patchedPrepareData(wrapped, ...args) {
libWrapper.register(MODULE_NAME, "CONFIG.Actor.documentClass.prototype.prepareData", function patchedPrepareData(wrapped, ...args) {
wrapped(...args);

const skills = this.data.data.skills;
Expand All @@ -34,7 +34,7 @@ function patchActor5ePrepareData() {
}

function patchActor5eRollSkill() {
libWrapper.register(MODULE_NAME, "CONFIG.Actor.entityClass.prototype.rollSkill", function patchedRollSkill(wrapped, ...args) {
libWrapper.register(MODULE_NAME, "CONFIG.Actor.documentClass.prototype.rollSkill", function patchedRollSkill(wrapped, ...args) {
const [ skillId, options ] = args;
const skillBonus = this.getFlag(MODULE_NAME, `${skillId}.${SKILL_BONUS_KEY}`);
if (skillBonus) {
Expand Down

0 comments on commit 10f4131

Please sign in to comment.