diff --git a/src/module/Constants.ts b/src/module/Constants.ts index a6947dd..5b54cf3 100644 --- a/src/module/Constants.ts +++ b/src/module/Constants.ts @@ -15,6 +15,7 @@ */ export const MODULE_NAME = `pf2e-toolbox`; +export const MODULE_TITLE = `PF2E Toolbox`; export const PF2E_PC_SHEET_NAME = `CharacterSheetPF2e`; export const PF2E_LOOT_SHEET_NAME = `LootSheetPF2e`; export const PF2E_NPC_SHEET_NAME = `NPCSheetPF2e`; diff --git a/src/module/Handlebars.ts b/src/module/Handlebars.ts index 8cf7861..ac1f195 100644 --- a/src/module/Handlebars.ts +++ b/src/module/Handlebars.ts @@ -1,3 +1,19 @@ +/* + * Copyright 2021 Andrew Cuccinello + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + import { MODULE_NAME } from './Constants'; export async function registerHandlebarsTemplates() { @@ -6,24 +22,6 @@ export async function registerHandlebarsTemplates() { `modules/${MODULE_NAME}/templates/roll-app/index.html`, `modules/${MODULE_NAME}/templates/roll-app/cell.html`, `modules/${MODULE_NAME}/templates/roll-app/table.html`, - `modules/${MODULE_NAME}/templates/loot-app/LootApp.html`, - `modules/${MODULE_NAME}/templates/loot-app/LootAppSidebar.html`, - `modules/${MODULE_NAME}/templates/loot-app/LootAppTreasure.html`, - `modules/${MODULE_NAME}/templates/loot-app/LootAppConsumables.html`, - `modules/${MODULE_NAME}/templates/loot-app/LootAppMagicItems.html`, - `modules/${MODULE_NAME}/templates/loot-app/LootAppScrolls.html`, - - `modules/${MODULE_NAME}/templates/settings-app/SettingsApp.html`, - `modules/${MODULE_NAME}/templates/settings-app/tabs/About.html`, - `modules/${MODULE_NAME}/templates/settings-app/tabs/Features.html`, - `modules/${MODULE_NAME}/templates/settings-app/tabs/License.html`, - - `modules/${MODULE_NAME}/templates/loot-app/create/CreateTab.html`, - `modules/${MODULE_NAME}/templates/loot-app/create/CreateShared.html`, - `modules/${MODULE_NAME}/templates/loot-app/create/CreateArmor.html`, - `modules/${MODULE_NAME}/templates/loot-app/create/CreateWeapon.html`, - `modules/${MODULE_NAME}/templates/loot-app/create/SelectRow.html`, - `modules/${MODULE_NAME}/templates/loot-app/create/RuneStats.html`, ]; await loadTemplates(templatePaths); diff --git a/src/module/Setup.ts b/src/module/Setup.ts index d97341d..b32960d 100644 --- a/src/module/Setup.ts +++ b/src/module/Setup.ts @@ -21,16 +21,15 @@ import { readyDefaultArt } from './features/DefaultArt'; import { setupQuantities } from './features/QuickQuantities'; import { setupFlattenProficiency } from './features/FlattenProficiency'; import { setupNPCScaler } from './features/NPCScaler'; -import { readyLootApp } from './features/LootApp'; import { setupHeroPoints } from './features/HeroPoints'; import { setupTokens } from './features/Tokens'; -import ModuleSettings, { ATTR_RELOAD_REQUIRED, ATTR_REOPEN_SHEET_REQUIRED, IFeatureDefinition } from '../../FVTT-Common/src/module/settings-app/ModuleSettings'; -import { MODULE_NAME } from './Constants'; +import { MODULE_NAME, MODULE_TITLE } from './Constants'; import { registerHandlebarsHelpers, registerHandlebarsTemplates } from './Handlebars'; import { fixMaterials, FixMaterials } from './commands/FixMaterials'; import secretSkillRoll from './macros/secret-skill-roll'; import { distributeHeroPoints } from './macros/distribute-hero-points'; import { groupSave, registerGroupSaveHooks } from './macros/group-saves'; +import ModuleSettings, { ATTR_RELOAD_REQUIRED, ATTR_REOPEN_SHEET_REQUIRED, IFeatureDefinition } from '../../FVTT-Common/src/module/ModuleSettings'; export const CREATURE_BUILDER = 'CREATURE_BUILDER'; export const FLATTEN_PROFICIENCY = 'FLATTEN_PROFICIENCY'; @@ -159,17 +158,6 @@ export const FEATURES: IFeatureDefinition[] = [ ], onSetup: setupNPCScaler, }, - { - id: LOOT_APP, - title: 'Loot Enhancements', - attributes: [ATTR_RELOAD_REQUIRED], - description: `Adds a new loot actor sheet with many enhancements such as a treasure roller, magic item creator, and more.`, - help: `You must set all loot actors back to the default sheet before disabling this option or the actor will not function after - it is disabled.`, - inputs: [], - register: [], - onReady: readyLootApp, - }, { id: HERO_POINTS, title: 'Maximum Hero Points', @@ -267,7 +255,12 @@ export const FEATURES: IFeatureDefinition[] = [ export const setup = () => { Hooks.on('init', () => { - ModuleSettings.instance.registerAllSettings(MODULE_NAME, FEATURES); + ModuleSettings.initialize({ + moduleName: MODULE_NAME, + moduleTitle: MODULE_TITLE, + features: FEATURES, + }); + ModuleSettings.instance.reg(LAST_SEEN_SYSTEM, { name: 'Last Seen System Version', scope: 'world', @@ -276,8 +269,8 @@ export const setup = () => { config: false, restricted: true, }); - ModuleSettings.instance.onInit(); }); + Hooks.on('setup', () => ModuleSettings.instance.onSetup()); Hooks.on('ready', () => ModuleSettings.instance.onReady()); @@ -323,4 +316,3 @@ export const setup = () => { registerGroupSaveHooks(); }); }; -// /pf2e-toolbox fix-materials diff --git a/src/module/commands/FixMaterials.ts b/src/module/commands/FixMaterials.ts index 0d87ba5..e537562 100644 --- a/src/module/commands/FixMaterials.ts +++ b/src/module/commands/FixMaterials.ts @@ -15,7 +15,7 @@ */ import { ChatCommand } from '../../../FVTT-Common/src/module/chat-command/ChatCommand'; -import ModuleSettings from '../../../FVTT-Common/src/module/settings-app/ModuleSettings'; +import ModuleSettings from '../../../FVTT-Common/src/module/ModuleSettings'; import { MATERIALS_FIXED } from '../Setup'; export class FixMaterials extends ChatCommand { diff --git a/src/module/cr-scaler/NPCScaler.ts b/src/module/cr-scaler/NPCScaler.ts index e5bc5ab..f9aba2c 100644 --- a/src/module/cr-scaler/NPCScaler.ts +++ b/src/module/cr-scaler/NPCScaler.ts @@ -17,7 +17,7 @@ import { IDataUpdates, IHandledItemType } from './NPCScalerTypes'; import { getActor, getFolder, getFolderInFolder } from '../Utilities'; import { getAreaDamageData, getDamageData, getHPData, getLeveledData, getMinMaxData } from './NPCScalerUtil'; -import ModuleSettings from '../../../FVTT-Common/src/module/settings-app/ModuleSettings'; +import ModuleSettings from '../../../FVTT-Common/src/module/ModuleSettings'; import { SCALED_FOLDER } from '../Setup'; const EMBEDDED_ENTITY_TYPE = 'Item'; diff --git a/src/module/features/DefaultArt.ts b/src/module/features/DefaultArt.ts index f009da2..3cd2369 100644 --- a/src/module/features/DefaultArt.ts +++ b/src/module/features/DefaultArt.ts @@ -14,8 +14,8 @@ * limitations under the License. */ -import ModuleSettings from '../../../FVTT-Common/src/module/settings-app/ModuleSettings'; import { LAST_SEEN_SYSTEM } from '../Setup'; +import ModuleSettings from '../../../FVTT-Common/src/module/ModuleSettings'; export async function readyDefaultArt() { if (game.system.data.version === ModuleSettings.instance.get(LAST_SEEN_SYSTEM)) { diff --git a/src/module/features/HeroPoints.ts b/src/module/features/HeroPoints.ts index 3bcd2d5..27c6f0b 100644 --- a/src/module/features/HeroPoints.ts +++ b/src/module/features/HeroPoints.ts @@ -15,7 +15,7 @@ */ import { PF2E_PC_SHEET_NAME } from '../Constants'; -import ModuleSettings from '../../../FVTT-Common/src/module/settings-app/ModuleSettings'; +import ModuleSettings from '../../../FVTT-Common/src/module/ModuleSettings'; import { MAX_HERO_POINTS } from '../Setup'; export const setupHeroPoints = () => Hooks.on(`render${PF2E_PC_SHEET_NAME}`, onSheetRender); diff --git a/src/module/features/LootApp.ts b/src/module/features/LootApp.ts deleted file mode 100644 index 0acb069..0000000 --- a/src/module/features/LootApp.ts +++ /dev/null @@ -1,28 +0,0 @@ -/* - * Copyright 2021 Andrew Cuccinello - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -import extendLootSheet from '../loot-app/LootApp'; -import { MODULE_NAME } from '../Constants'; - -export function readyLootApp() { - const LootApp = extendLootSheet(); - - // @ts-ignore - Actors.registerSheet(MODULE_NAME, LootApp, { - types: ['loot'], - makeDefault: false, - }); -} diff --git a/src/module/features/QuickQuantities.ts b/src/module/features/QuickQuantities.ts index d0923e9..21f5f90 100644 --- a/src/module/features/QuickQuantities.ts +++ b/src/module/features/QuickQuantities.ts @@ -14,7 +14,7 @@ * limitations under the License. */ -import ModuleSettings from '../../../FVTT-Common/src/module/settings-app/ModuleSettings'; +import ModuleSettings from '../../../FVTT-Common/src/module/ModuleSettings'; import { CONTROL_QUANTITY, SHIFT_QUANTITY } from '../Setup'; export const setupQuantities = () => Hooks.on('renderActorSheet', onQuantitiesHook); diff --git a/src/module/features/Tokens.ts b/src/module/features/Tokens.ts index c8ea1d1..1f1b479 100644 --- a/src/module/features/Tokens.ts +++ b/src/module/features/Tokens.ts @@ -14,7 +14,7 @@ * limitations under the License. */ -import ModuleSettings from '../../../FVTT-Common/src/module/settings-app/ModuleSettings'; +import ModuleSettings from '../../../FVTT-Common/src/module/ModuleSettings'; import { TOKEN_PATH, TOKEN_TARGET, TOKEN_TARGET_BUCKET } from '../Setup'; export const setupTokens = () => Hooks.on('getActorDirectoryEntryContext', onSetupTokensContextHook); diff --git a/src/module/loot-app/LootApp.ts b/src/module/loot-app/LootApp.ts deleted file mode 100644 index bfff95a..0000000 --- a/src/module/loot-app/LootApp.ts +++ /dev/null @@ -1,575 +0,0 @@ -/* - * Copyright 2021 Andrew Cuccinello - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -import { MODULE_NAME, PF2E_LOOT_SHEET_NAME } from '../Constants'; -import { GetItemFromCollection, GetMagicItemTables, GetTreasureTables } from './LootAppUtil'; -import { CREATE_KEY_NONE, CREATE_MODES, CreateMode, IGradeStats, ITEM_GRADES, ITEM_MATERIALS, ITEM_RUNES } from './LootAppData'; -import ModuleSettings from '../../../FVTT-Common/src/module/settings-app/ModuleSettings'; -import { FEATURES, QUICK_MYSTIFY } from '../Setup'; - -type IMaterials = typeof ITEM_MATERIALS; -type IMaterial = IMaterials[keyof typeof ITEM_MATERIALS]; - -const CREATE_MODE = 'create-mode'; - -const KEY_ITE = 'create-baseItem'; -const KEY_MAT = 'create-material'; -const KEY_GRD = 'create-grade'; -const KEY_POT = 'create-potency'; -const KEY_FUN = 'create-fundamental'; -const KEY_RU1 = 'create-property1'; -const KEY_RU2 = 'create-property2'; -const KEY_RU3 = 'create-property3'; - -interface SelectOption { - id: string; - label: string; -} - -const itemToOption = (item: Item): SelectOption => { - return { - id: item.id as string, - label: item.name as string, - }; -}; -const materialToOption = (mat: IMaterial): SelectOption => { - return { - id: mat.id, - label: mat.label, - }; -}; - -const materialHasGrade = (materialKey: string, gradeKey: string): boolean => { - return ITEM_MATERIALS[materialKey]?.hasOwnProperty(gradeKey); -}; - -const getItemPrice = (stringValue: string): number => { - const [value, denomination] = stringValue.split(' '); - if (denomination === 'pp') return parseInt(value) * 10; - if (denomination === 'gp') return parseInt(value); - if (denomination === 'sp') return parseInt(value) / 10; - if (denomination === 'cp') return parseInt(value) / 100; - return parseInt(value); -}; -const getMaterialPrice = (bulkString: string, pricePerBulk: number): number => { - let bulkNumber; - if (bulkString === '-') bulkNumber = 0; - else if (bulkString === 'L') bulkNumber = 0.1; - else bulkNumber = parseInt(bulkString); - - return bulkNumber * pricePerBulk; -}; - -export default function extendLootSheet() { - type ActorSheetConstructor = new (...args: any[]) => ActorSheet; - // @ts-ignore - const extendMe: ActorSheetConstructor = CONFIG.Actor.sheetClasses['loot'][`pf2e.${PF2E_LOOT_SHEET_NAME}`].cls; - return class LootApp extends extendMe { - static get defaultOptions() { - // @ts-ignore - const options = super.defaultOptions; - options.classes = options.classes ?? []; - options.classes = [...options.classes, 'pf2e-toolbox', 'loot-app']; - - options.tabs = options.tabs ?? []; - options.tabs = [...options.tabs, { navSelector: '.loot-app-nav', contentSelector: '.loot-app-content', initial: 'loot-config' }]; - return options; - } - - cacheContent: Item[] | undefined; - - get template() { - const editableSheetPath = `modules/${MODULE_NAME}/templates/loot-app/LootApp.html`; - const nonEditableSheetPath = 'systems/pf2e/templates/actors/loot/sheet.html'; - - const isEditable = this.actor.getFlag('pf2e', 'editLoot.value'); - - if (isEditable || game.user?.isGM) { - return editableSheetPath; - } - - return nonEditableSheetPath; - } - - get createMode(): CreateMode { - return (this.actor.getFlag(MODULE_NAME, CREATE_MODE) as CreateMode) ?? CreateMode.Weapon; - } - - get selIteKey(): string { - return (this.actor.getFlag(MODULE_NAME, KEY_ITE) as string) ?? CREATE_KEY_NONE; - } - get selMatKey(): string { - return (this.actor.getFlag(MODULE_NAME, KEY_MAT) as string) ?? CREATE_KEY_NONE; - } - get selGrdKey(): string { - return (this.actor.getFlag(MODULE_NAME, KEY_GRD) as string) ?? CREATE_KEY_NONE; - } - get selPotKey(): string { - return (this.actor.getFlag(MODULE_NAME, KEY_POT) as string) ?? CREATE_KEY_NONE; - } - get selFunKey(): string { - return (this.actor.getFlag(MODULE_NAME, KEY_FUN) as string) ?? CREATE_KEY_NONE; - } - - async getSelectedItem(): Promise { - const equipment = await this.getEquipmentContent(); - - const id = this.selIteKey; - return equipment.find((i) => i.id === id); - } - - async getEquipmentContent(): Promise { - // cache content to avoid 2-3s delay on .getContent - if (this.cacheContent) { - return this.cacheContent; - } - - const equipment = game.packs.get('pf2e.equipment-srd') as unknown as Compendium; - this.cacheContent = (await equipment.getContent()) as unknown as Item[]; - return this.cacheContent; - } - - async collectBaseArmors(): Promise { - const equipmentContent = await this.getEquipmentContent(); - return equipmentContent - .filter((i) => { - if (i.data.type !== 'armor') return false; - // 3 exceptions to the 0 level rule - if (['Full Plate', 'Half Plate', 'Splint Mail'].includes(i.data.name)) return true; - if (i.data.data['level'].value > 0) return false; - return true; - }) - .map(itemToOption); - } - - async collectBaseWeapons(): Promise { - const equipmentContent = await this.getEquipmentContent(); - return equipmentContent - .filter((i) => { - if (i.data.type !== 'weapon') return false; - if (i.data.name === 'Aldori Dueling Sword') return true; - if (i.data.data['level'].value > 0) return false; - if (['bomb'].includes(i.data.data['value'])) return false; - return true; - }) - .map(itemToOption); - } - - // @ts-ignore - getData() { - return new Promise(async (resolve) => { - const renderData = await super.getData(); - - renderData['treasureTables'] = await GetTreasureTables(); - // Quick Mystification breaks when these are enabled, investigate. - renderData['magicItemTables'] = await GetMagicItemTables('Permanent Items'); - renderData['consumablesTables'] = await GetMagicItemTables('Consumables'); - - renderData['flags'] = this.actor.data.flags; - - renderData['create'] = { - mode: this.createMode, - modes: CREATE_MODES, - }; - - if (this.selMatKey && !materialHasGrade(this.selMatKey, this.selGrdKey)) { - await this.actor.setFlag(MODULE_NAME, KEY_GRD, ITEM_MATERIALS[this.selMatKey].defaultGrade); - } - - // Item materials - renderData['create']['material'] = ITEM_MATERIALS[this.selMatKey]; - renderData['create']['materialOptions'] = Object.keys(ITEM_MATERIALS).map((key) => { - return { - id: ITEM_MATERIALS[key].id, - label: ITEM_MATERIALS[key].label, - }; - }); - - // Material hardness, hp, bt - let material = ITEM_MATERIALS[this.selMatKey] as IMaterial | undefined; - if (material === undefined) { - material = ITEM_MATERIALS['metal']; - } - - let materialGradeStats = material[this.selGrdKey] as IGradeStats | undefined; - if (materialGradeStats === undefined) { - materialGradeStats = material[material.defaultGrade] as IGradeStats; - } - - let thicknessKey = this.createMode === CreateMode.Weapon ? 'thinItems' : 'items'; - if (thicknessKey === 'thinItems' && materialGradeStats[thicknessKey] === undefined) { - thicknessKey = 'items'; - } - - renderData['create']['materialHardness'] = materialGradeStats[thicknessKey].hardness; - renderData['create']['materialHp'] = materialGradeStats[thicknessKey].hp; - renderData['create']['materialBt'] = materialGradeStats[thicknessKey].bt; - renderData['create']['materialPrice'] = materialGradeStats.pricePerBulk; - - // Material grades - renderData['create']['grade'] = ITEM_GRADES[this.selGrdKey]; - renderData['create']['gradeOptions'] = Object.keys(ITEM_GRADES) - .filter((grade) => materialHasGrade(this.selMatKey, grade)) - .map((key) => { - return { - id: ITEM_GRADES[key].id, - label: ITEM_GRADES[key].label, - }; - }); - - // Item runes - renderData['create']['runes'] = ITEM_RUNES; - - // Base item - const baseItem = await this.getSelectedItem(); - renderData['create']['baseItem'] = baseItem; - if (baseItem) { - renderData['create']['baseItemLevel'] = parseInt(baseItem.data.data['level'].value); - renderData['create']['baseItemPrice'] = getItemPrice(baseItem.data.data['price'].value); - } - - let items: SelectOption[]; - switch (this.createMode) { - case CreateMode.Weapon: - items = await this.collectBaseWeapons(); - renderData['create']['baseItemOptions'] = items; - break; - case CreateMode.Armor: - items = await this.collectBaseArmors(); - renderData['create']['baseItemOptions'] = items; - break; - } - - if (!items.find((i) => i.id === this.selIteKey)) { - await this.actor.setFlag(MODULE_NAME, KEY_ITE, items[0].id); - } - - const getRuneData = async (name: string, key: string) => { - const selKey = this.actor.getFlag(MODULE_NAME, `${key}`) as string | undefined; - if (!selKey) return; - - let rune = ITEM_RUNES[this.createMode].property[selKey]; - if (rune === undefined) { - await this.actor.setFlag(MODULE_NAME, key, CREATE_KEY_NONE); - return; - } - - renderData['create'][name] = rune; - renderData['create'][`${name}Level`] = rune.level; - renderData['create'][`${name}Price`] = rune.price; - }; - - // Item potency - const potency = ITEM_RUNES[this.createMode].potency[this.selPotKey]; - renderData['create']['potency'] = potency; - renderData['create']['potencyOptions'] = ITEM_RUNES[this.createMode].potency; - renderData['create']['potencyLevel'] = potency.level; - renderData['create']['potencyPrice'] = potency.price; - - // Fundamental runes - let fundamental = ITEM_RUNES[this.createMode].fundamental[this.selFunKey]; - if (fundamental === undefined) { - await this.actor.setFlag(MODULE_NAME, KEY_FUN, CREATE_KEY_NONE); - fundamental = ITEM_RUNES[this.createMode].fundamental[this.selFunKey]; - } - - renderData['create']['fundamental'] = fundamental; - renderData['create']['fundamentalOptions'] = ITEM_RUNES[this.createMode].fundamental; - renderData['create']['fundamentalLevel'] = fundamental.level; - renderData['create']['fundamentalPrice'] = fundamental.price; - - if (potency.nId === 0 && this.actor.getFlag(MODULE_NAME, KEY_FUN) !== CREATE_KEY_NONE) { - await this.actor.setFlag(MODULE_NAME, KEY_FUN, CREATE_KEY_NONE); - } - - // Item property - for (let i = 3; i > 0; i--) { - const key = `create-property${i}`; - if (potency.nId < i && this.actor.getFlag(MODULE_NAME, key) !== CREATE_KEY_NONE) { - await this.actor.setFlag(MODULE_NAME, key, CREATE_KEY_NONE); - } - } - - renderData['create']['propertyOptions'] = ITEM_RUNES[this.createMode].property; - await getRuneData('property1', KEY_RU1); - await getRuneData('property2', KEY_RU2); - await getRuneData('property3', KEY_RU3); - - renderData['create']['itemPrice'] = renderData['create']['baseItemPrice']; - renderData['create']['itemLevel'] = renderData['create']['baseItemLevel']; - - renderData['create']['itemPrice'] += getMaterialPrice(baseItem?.data.data['weight'].value, materialGradeStats.pricePerBulk); - - renderData['create']['itemPrice'] += renderData['create']['potencyPrice']; - renderData['create']['itemLevel'] = Math.max(renderData['create']['itemLevel'], renderData['create'][`potencyLevel`]); - - renderData['create']['itemPrice'] += renderData['create']['fundamentalPrice']; - renderData['create']['itemLevel'] = Math.max(renderData['create']['itemLevel'], renderData['create'][`fundamentalLevel`]); - - for (let i = 1; i < 4; i++) { - const price = `property${i}Price`; - const level = `property${i}Level`; - - if (renderData['create'][price]) { - renderData['create']['itemPrice'] += renderData['create'][price]; - } - if (renderData['create'][level]) { - renderData['create']['itemLevel'] = Math.max(renderData['create']['itemLevel'], renderData['create'][level]); - } - } - - renderData['create']['itemRarity'] = baseItem?.data.data['traits'].rarity.value.capitalize(); - if (renderData['create']['itemLevel'] === 25) { - renderData['create']['itemRarity'] = 'Unique'; - } - - resolve(renderData); - }); - } - - async createCustomItem(event: JQuery.ClickEvent): Promise { - const getFlag = (key: string): any => { - return this.actor.getFlag(MODULE_NAME, key); - }; - const getSelected = (key: string): string => { - return getFlag(key) ?? CREATE_KEY_NONE; - }; - - const baseItem = (await this.getSelectedItem()) as Item; - const newItemData = duplicate(baseItem?.data) as any; - - let itemPrice = getItemPrice(baseItem.data.data['price'].value); - let itemLevel = parseInt(baseItem.data.data['level'].value); - - const material = ITEM_MATERIALS[this.selMatKey]; - const gradeStats = material[this.selGrdKey] as IGradeStats; - let thicknessKey = this.createMode === CreateMode.Weapon ? 'thinItems' : 'items'; - if (thicknessKey === 'thinItems' && gradeStats[thicknessKey] === undefined) { - thicknessKey = 'items'; - } - - newItemData.data.hardness.value = gradeStats[thicknessKey].hardness; - newItemData.data.brokenThreshold.value = gradeStats[thicknessKey].bt; - newItemData.data.hp.value = gradeStats[thicknessKey].hp; - newItemData.data.maxHp.value = gradeStats[thicknessKey].hp; - - newItemData.data.preciousMaterial.value = material.id; - newItemData.data.preciousMaterialGrade.value = this.selGrdKey; - - itemPrice += getMaterialPrice(baseItem.data.data['weight'].value, gradeStats.pricePerBulk); - - let potencyRune = ITEM_RUNES[this.createMode].potency[this.selPotKey]; - newItemData.data.potencyRune.value = this.selPotKey; - - itemPrice += potencyRune.price; - itemLevel = Math.max(itemLevel, potencyRune.level); - - switch (this.createMode) { - case CreateMode.Weapon: - newItemData.data.strikingRune.value = this.selFunKey; - break; - case CreateMode.Armor: - newItemData.data.resiliencyRune.value = this.selFunKey; - break; - } - - let propertyRune1 = ITEM_RUNES[this.createMode].property[getSelected(KEY_RU1)]; - let propertyRune2 = ITEM_RUNES[this.createMode].property[getSelected(KEY_RU2)]; - let propertyRune3 = ITEM_RUNES[this.createMode].property[getSelected(KEY_RU3)]; - let fundamentalRune = ITEM_RUNES[this.createMode].fundamental[getSelected(KEY_FUN)]; - - newItemData.data.propertyRune1.value = propertyRune1.id; - newItemData.data.propertyRune2.value = propertyRune2.id; - newItemData.data.propertyRune3.value = propertyRune3.id; - - itemPrice += propertyRune1.price; - itemPrice += propertyRune2.price; - itemPrice += propertyRune3.price; - itemPrice += fundamentalRune.price; - - itemLevel = Math.max(itemLevel, propertyRune1.level); - itemLevel = Math.max(itemLevel, propertyRune1.level); - itemLevel = Math.max(itemLevel, propertyRune1.level); - - let itemName = baseItem.name; - - for (let i = 3; i > 0; i--) { - const key = `create-property${i}`; - const keyRu = this.actor.getFlag(MODULE_NAME, key) as string; - if (potencyRune.nId >= i && keyRu !== CREATE_KEY_NONE) { - const rune = ITEM_RUNES[this.createMode].property[keyRu]; - itemName = `${rune.label} ${itemName}`; - } - } - - if (fundamentalRune.id !== CREATE_KEY_NONE) { - itemName = `${fundamentalRune.label} ${itemName}`; - } - - if (potencyRune.nId > 0) { - itemName = `+${potencyRune.nId} ${itemName}`; - } - - newItemData.data.level.value = itemLevel; - newItemData.data.price.value = `${itemPrice} gp`; - - if (itemLevel === 25) { - newItemData.data.traits.rarity.value = 'unique'; - newItemData.data.price.value = `—`; - } - - newItemData.name = itemName; - - if (event.altKey && ModuleSettings.instance.get(QUICK_MYSTIFY)) { - newItemData.data.identification = { - status: 'unidentified', - identified: { - name: newItemData.name, - }, - }; - - let newName: string = newItemData.type === 'weapon' ? newItemData.data.group.value : newItemData.data.armorType.value; - newName = newName.capitalize(); - - newItemData.name = `Unidentified ${newName}`; - } - - await this.actor.createOwnedItem(newItemData, {}); - } - - activateListeners(html: JQuery) { - super.activateListeners(html); - - html.find('select').on('input', (event) => { - this._onSubmit(event as unknown as Event); - }); - - html.find('#create').on('click', (event) => { - this.createCustomItem(event); - }); - - const actor = this.actor as Actor; - html.find('button.roll-single-table').on('click', async (event) => { - event.preventDefault(); - - const button = $(event.currentTarget) as JQuery; - const tableId = button.data('entity-id') as string; - const drawCount = Number(button.data('count')); - - const table = (await GetItemFromCollection('pf2e.rollable-tables', tableId)) as RollTable; - - // @ts-ignore - let rolls = await table.drawMany(drawCount); - - const promises = rolls.results.map((r) => { - return GetItemFromCollection(r.data.collection, r.data.resultId); - }); - - let entities: (Entity | null)[] = await Promise.all(promises); - - let filtered = entities.filter((i) => i !== null && i !== undefined) as Entity[]; - - if (filtered.length !== drawCount) { - // @ts-ignore - ui.notifications.warn('Found one or more items in the rollable table that do not exist in the compendium, skipping these.'); - } - - let results = filtered.map((i) => i.data); - - results = results.map((i) => { - // @ts-ignore - if (!i.data['value'].value) { - return i; - } - - const roll = new Roll('1d4').roll(); - // @ts-ignore - i.data['value'].value = roll.total * i.data['value'].value; - return i; - }); - - if (ModuleSettings.instance.get(QUICK_MYSTIFY) && event.altKey) { - for (const item of results) { - item['data']['identification'] = { - status: 'unidentified', - identified: { - name: item.name, - }, - }; - let newName = item.type.capitalize(); - item.name = `Unidentified ${newName}`; - } - } - - // @ts-ignore - await actor.createEmbeddedDocuments('Item', results); - }); - html.find('button.roll-magic-item').on('click', async (event) => { - event.preventDefault(); - - const button = $(event.currentTarget) as JQuery; - const tableId = button.data('entity-id') as string; - const drawCount = Number(button.data('count')); - - const table = (await GetItemFromCollection('pf2e.rollable-tables', tableId)) as RollTable; - - // @ts-ignore - let rolls = await table.drawMany(drawCount); - const promises = rolls.results.map((r) => { - if (!r.data.hasOwnProperty('collection')) { - return Promise.resolve(null); - } - return GetItemFromCollection(r.data.collection, r.data.resultId); - }); - - let entities: (Entity | null)[] = await Promise.all(promises); - - let filtered = entities.filter((i) => i !== null && i !== undefined) as Entity[]; - - if (filtered.length !== drawCount) { - ui?.notifications?.warn( - 'PF2EToolbox drew a custom weapon, custom armor, or typed potion, but these are not supported. One or more rolls has been skipped.', - ); - } - - let results = filtered.map((i) => i.data); - - if (ModuleSettings.instance.get(QUICK_MYSTIFY) && event.altKey) { - for (const item of results) { - item['data']['identification'] = { - status: 'unidentified', - identified: { - name: item.name, - }, - }; - let newName = item.type.capitalize(); - item.name = `Unidentified ${newName}`; - } - } - - // @ts-ignore - await actor.createEmbeddedDocuments('Item', results); - - await new Promise((resolve) => setTimeout(resolve, 1000)); - }); - - html.find('button.clear-inventory').on('click', async (event) => { - // @ts-ignore - await actor.deleteEmbeddedDocuments('Item', actor.items.map((i) => i.id) as string[]); - }); - } - }; -} diff --git a/src/module/loot-app/LootAppData.ts b/src/module/loot-app/LootAppData.ts deleted file mode 100644 index 353edb5..0000000 --- a/src/module/loot-app/LootAppData.ts +++ /dev/null @@ -1,742 +0,0 @@ -export enum CreateMode { - Weapon = 'weapon', - Armor = 'armor', - // Scroll = 'scroll' -} -export const CREATE_MODES = [CreateMode.Weapon, CreateMode.Armor]; - -export interface IMaterialMap { - [key: string]: IMaterial; -} -export interface IMaterial { - id: string; - label: string; - defaultGrade: 'low' | 'standard' | 'high'; - low?: IGradeStats; - standard?: IGradeStats; - high?: IGradeStats; -} -export interface IThicknessStats { - hardness: number; - hp: number; - bt: number; -} -export interface IGradeStats { - pricePerBulk: number; - thinItems?: IThicknessStats; - items: IThicknessStats; - structure?: IThicknessStats; -} - -export const ITEM_MATERIALS: IMaterialMap = { - cloth: { - id: 'cloth', - label: 'Cloth', - defaultGrade: 'standard', - standard: { - pricePerBulk: 0, - thinItems: { hardness: 0, hp: 1, bt: 0 }, - items: { hardness: 1, hp: 4, bt: 2 }, - }, - }, - leather: { - id: 'leather', - label: 'Leather', - defaultGrade: 'standard', - standard: { - pricePerBulk: 0, - items: { hardness: 4, hp: 16, bt: 8 }, - }, - }, - metal: { - id: 'metal', - label: 'Metal', - defaultGrade: 'standard', - standard: { - pricePerBulk: 0, - items: { hardness: 9, hp: 36, bt: 18 }, - }, - }, - wood: { - id: 'wood', - label: 'Wood', - defaultGrade: 'standard', - standard: { - pricePerBulk: 0, - items: { hardness: 5, hp: 20, bt: 10 }, - }, - }, - adamantine: { - id: 'adamantine', - label: 'Adamantine', - defaultGrade: 'standard', - standard: { - pricePerBulk: 350, - thinItems: { hardness: 10, hp: 40, bt: 20 }, - items: { hardness: 14, hp: 56, bt: 28 }, - structure: { hardness: 28, hp: 112, bt: 56 }, - }, - high: { - pricePerBulk: 6000, - thinItems: { hardness: 13, hp: 52, bt: 26 }, - items: { hardness: 17, hp: 68, bt: 34 }, - structure: { hardness: 34, hp: 136, bt: 68 }, - }, - }, - coldIron: { - id: 'coldIron', - label: 'Cold Iron', - defaultGrade: 'standard', - low: { - pricePerBulk: 20, - thinItems: { hardness: 5, hp: 20, bt: 10 }, - items: { hardness: 9, hp: 36, bt: 18 }, - structure: { hardness: 18, hp: 72, bt: 36 }, - }, - standard: { - pricePerBulk: 250, - thinItems: { hardness: 7, hp: 28, bt: 14 }, - items: { hardness: 11, hp: 44, bt: 22 }, - structure: { hardness: 22, hp: 88, bt: 44 }, - }, - high: { - pricePerBulk: 4500, - thinItems: { hardness: 10, hp: 40, bt: 20 }, - items: { hardness: 14, hp: 56, bt: 28 }, - structure: { hardness: 28, hp: 112, bt: 56 }, - }, - }, - darkwood: { - id: 'darkwood', - label: 'Darkwood', - defaultGrade: 'standard', - standard: { - pricePerBulk: 350, - thinItems: { hardness: 5, hp: 20, bt: 10 }, - items: { hardness: 7, hp: 28, bt: 14 }, - structure: { hardness: 14, hp: 56, bt: 28 }, - }, - high: { - pricePerBulk: 6000, - thinItems: { hardness: 8, hp: 32, bt: 16 }, - items: { hardness: 10, hp: 40, bt: 20 }, - structure: { hardness: 20, hp: 80, bt: 40 }, - }, - }, - dragonhide: { - id: 'dragonhide', - label: 'Dragonhide', - defaultGrade: 'standard', - standard: { - pricePerBulk: 350, - thinItems: { hardness: 4, hp: 16, bt: 8 }, - items: { hardness: 7, hp: 28, bt: 14 }, - }, - high: { - pricePerBulk: 6000, - thinItems: { hardness: 8, hp: 32, bt: 16 }, - items: { hardness: 11, hp: 44, bt: 22 }, - }, - }, - mithral: { - id: 'mithral', - label: 'Mithral', - defaultGrade: 'standard', - standard: { - pricePerBulk: 350, - thinItems: { hardness: 5, hp: 20, bt: 10 }, - items: { hardness: 9, hp: 36, bt: 18 }, - structure: { hardness: 18, hp: 72, bt: 36 }, - }, - high: { - pricePerBulk: 6000, - thinItems: { hardness: 8, hp: 32, bt: 16 }, - items: { hardness: 12, hp: 48, bt: 24 }, - structure: { hardness: 24, hp: 96, bt: 48 }, - }, - }, - orichalcum: { - id: 'orichalcum', - label: 'Orichalcum', - defaultGrade: 'high', - high: { - pricePerBulk: 10000, - thinItems: { hardness: 16, hp: 64, bt: 32 }, - items: { hardness: 18, hp: 72, bt: 36 }, - structure: { hardness: 35, hp: 140, bt: 70 }, - }, - }, - silver: { - id: 'silver', - label: 'Silver', - defaultGrade: 'standard', - low: { - pricePerBulk: 20, - thinItems: { hardness: 3, hp: 12, bt: 6 }, - items: { hardness: 5, hp: 20, bt: 10 }, - structure: { hardness: 10, hp: 40, bt: 20 }, - }, - standard: { - pricePerBulk: 250, - thinItems: { hardness: 5, hp: 20, bt: 10 }, - items: { hardness: 7, hp: 28, bt: 14 }, - structure: { hardness: 14, hp: 56, bt: 28 }, - }, - high: { - pricePerBulk: 4500, - thinItems: { hardness: 8, hp: 32, bt: 16 }, - items: { hardness: 10, hp: 40, bt: 20 }, - structure: { hardness: 20, hp: 80, bt: 40 }, - }, - }, - sovereignSteel: { - //TODO: PF2E has id of 'sovereign steel' - id: 'sovereignSteel', - label: 'Sovereign Steel', - defaultGrade: 'standard', - standard: { - pricePerBulk: 500, - thinItems: { hardness: 7, hp: 28, bt: 14 }, - items: { hardness: 11, hp: 44, bt: 22 }, - structure: { hardness: 22, hp: 88, bt: 44 }, - }, - high: { - pricePerBulk: 8000, - thinItems: { hardness: 10, hp: 40, bt: 20 }, - items: { hardness: 14, hp: 56, bt: 28 }, - structure: { hardness: 28, hp: 112, bt: 56 }, - }, - }, -}; - -export interface IGrade { - id: string; - label: string; -} -export interface IGradesMap { - [key: string]: IGrade; -} -export const ITEM_GRADES: IGradesMap = { - low: { - id: 'low', - label: 'Low-grade', - }, - standard: { - id: 'standard', - label: 'Standard-grade', - }, - high: { - id: 'high', - label: 'High-grade', - }, -}; - -export const CREATE_KEY_NONE = ''; -const CREATE_OBJECT_NONE = { - id: CREATE_KEY_NONE, - nId: 0, - label: 'None', - price: 0, - level: 0, -}; -export const ITEM_RUNES = { - [CreateMode.Weapon]: { - potency: { - [CREATE_KEY_NONE]: { - ...CREATE_OBJECT_NONE, - }, - '1': { - id: '1', - nId: 1, - label: 'Weapon Potency (+1)', - level: 2, - price: 35, - }, - '2': { - id: '2', - nId: 2, - label: 'Weapon Potency (+2)', - level: 10, - price: 935, - }, - '3': { - id: '3', - nId: 3, - label: 'Weapon Potency (+3)', - level: 16, - price: 8935, - }, - '4': { - id: '4', - nId: 4, - label: 'Weapon Potency (+4)', - level: 25, - price: 0, - }, - }, - fundamental: { - [CREATE_KEY_NONE]: { - ...CREATE_OBJECT_NONE, - }, - striking: { - nId: 1, - id: 'striking', - label: 'striking', - price: 65, - level: 4, - }, - greaterStriking: { - nId: 2, - id: 'greaterStriking', - label: 'greater striking', - price: 1065, - level: 12, - }, - majorStriking: { - nId: 3, - id: 'majorStriking', - label: 'major striking', - price: 31065, - level: 19, - }, - }, - property: { - [CREATE_KEY_NONE]: { - ...CREATE_OBJECT_NONE, - }, - anarchic: { - id: 'anarchic', - label: 'anarchic', - price: 1400, - level: 11, - }, - ancestralEchoing: { - id: 'ancestralEchoing', - label: 'ancestral echoing', - price: 9500, - level: 15, - }, - axiomatic: { - id: 'axiomatic', - label: 'axiomatic', - price: 1400, - level: 11, - }, - bloodbane: { - id: 'bloodbane', - label: 'bloodbane', - price: 475, - level: 8, - }, - corrosive: { - id: 'corrosive', - label: 'corrosive', - price: 500, - level: 8, - }, - dancing: { - id: 'dancing', - label: 'dancing', - price: 2700, - level: 13, - }, - disrupting: { - id: 'disrupting', - label: 'disrupting', - price: 150, - level: 5, - }, - fearsome: { - id: 'fearsome', - label: 'fearsome', - price: 160, - level: 5, - }, - flaming: { - id: 'flaming', - label: 'flaming', - price: 500, - level: 8, - }, - frost: { - id: 'frost', - label: 'frost', - price: 500, - level: 8, - }, - ghostTouch: { - id: 'ghostTouch', - label: 'ghost touch', - price: 75, - level: 4, - }, - greaterBloodbane: { - id: 'greaterBloodbane', - label: 'greater bloodbane', - price: 6500, - level: 15, - }, - greaterCorrosive: { - id: 'greaterCorrosive', - label: 'greater corrosive', - price: 6500, - level: 15, - }, - greaterDisrupting: { - id: 'greaterDisrupting', - label: 'greater disrupting', - price: 4300, - level: 14, - }, - greaterFearsome: { - id: 'greaterFearsome', - label: 'greater fearsome', - price: 2000, - level: 12, - }, - greaterFlaming: { - id: 'greaterFlaming', - label: 'greater flaming', - price: 6500, - level: 15, - }, - greaterFrost: { - id: 'greaterFrost', - label: 'greater frost', - price: 6500, - level: 15, - }, - greaterShock: { - id: 'greaterShock', - label: 'greater shock', - price: 6500, - level: 15, - }, - greaterThundering: { - id: 'greaterThundering', - label: 'greater thundering', - price: 6500, - level: 15, - }, - grievous: { - id: 'grievous', - label: 'grievous', - price: 700, - level: 9, - }, - holy: { - id: 'holy', - label: 'holy', - price: 1400, - level: 11, - }, - keen: { - id: 'keen', - label: 'keen', - price: 3000, - level: 13, - }, - kinWarding: { - id: 'kinWarding', - label: 'kin-warding', - price: 52, - level: 3, - }, - pacifying: { - id: 'pacifying', - label: 'pacifying', - price: 150, - level: 5, - }, - returning: { - id: 'returning', - label: 'returning', - price: 55, - level: 3, - }, - serrating: { - id: 'serrating', - label: 'serrating', - price: 1000, - level: 10, - }, - shifting: { - id: 'shifting', - label: 'shifting', - price: 225, - level: 6, - }, - shock: { - id: 'shock', - label: 'shock', - price: 500, - level: 8, - }, - speed: { - id: 'speed', - label: 'speed', - price: 10000, - level: 16, - }, - spellStoring: { - id: 'spellStoring', - label: 'spell-storing', - price: 2700, - level: 13, - }, - thundering: { - id: 'thundering', - label: 'thundering', - price: 500, - level: 8, - }, - unholy: { - id: 'unholy', - label: 'unholy', - price: 1400, - level: 11, - }, - vorpal: { - id: 'vorpal', - label: 'vorpal', - price: 15000, - level: 17, - }, - wounding: { - id: 'wounding', - label: 'wounding', - price: 340, - level: 7, - }, - }, - }, - [CreateMode.Armor]: { - potency: { - [CREATE_KEY_NONE]: { - ...CREATE_OBJECT_NONE, - }, - '1': { - id: '1', - nId: 1, - label: 'Armor Potency (+1)', - level: 5, - price: 160, - }, - '2': { - id: '2', - nId: 2, - label: 'Armor Potency (+2)', - level: 11, - price: 1060, - }, - '3': { - id: '3', - nId: 3, - label: 'Armor Potency (+3)', - level: 18, - price: 20560, - }, - '4': { - id: '4', - nId: 4, - label: 'Armor Potency (+4)', - level: 25, - price: 0, - }, - }, - fundamental: { - [CREATE_KEY_NONE]: { - ...CREATE_OBJECT_NONE, - }, - resilient: { - nId: 1, - id: 'resilient', - label: 'resilient', - level: 8, - price: 340, - }, - greaterResilient: { - nId: 2, - id: 'greaterResilient', - label: 'greater resilient', - level: 14, - price: 3440, - }, - majorResilient: { - nId: 3, - id: 'majorResilient', - label: 'major resilient', - level: 20, - price: 49440, - }, - }, - property: { - [CREATE_KEY_NONE]: { - ...CREATE_OBJECT_NONE, - }, - acidResistant: { - id: 'acidResistant', - label: 'acid-resistant', - price: 420, - level: 8, - }, - antimagic: { - id: 'antimagic', - label: 'antimagic', - price: 6500, - level: 15, - }, - coldResistant: { - id: 'coldResistant', - label: 'cold-resistant', - price: 420, - level: 8, - }, - electricityResistant: { - id: 'electricityResistant', - label: 'electricity-resistant', - price: 420, - level: 8, - }, - ethereal: { - id: 'ethereal', - label: 'ethereal', - price: 13500, - level: 17, - }, - fireResistant: { - id: 'fireResistant', - label: 'fire-resistant', - price: 420, - level: 8, - }, - fortification: { - id: 'fortification', - label: 'fortification', - price: 2000, - level: 12, - }, - glamered: { - id: 'glamered', - label: 'glamered', - price: 140, - level: 5, - }, - greaterAcidResistant: { - id: 'greaterAcidResistant', - label: 'greater acid-resistant', - price: 1650, - level: 12, - }, - greaterColdResistant: { - id: 'greaterColdResistant', - label: 'greater cold-resistant', - price: 1650, - level: 12, - }, - greaterElectricityResistant: { - id: 'greaterElectricityResistant', - label: 'greater electricity-resistant', - price: 1650, - level: 12, - }, - greaterFireResistant: { - id: 'greaterFireResistant', - label: 'greater fire-resistant', - price: 1650, - level: 12, - }, - greaterFortification: { - id: 'greaterFortification', - label: 'greater fortification', - price: 24000, - level: 18, - }, - greaterInvisibility: { - id: 'greaterInvisibility', - label: 'greater invisibility', - price: 1000, - level: 10, - }, - greaterReady: { - id: 'greaterReady', - label: 'greater ready', - price: 1200, - level: 11, - }, - greaterShadow: { - id: 'greaterShadow', - label: 'greater shadow', - price: 650, - level: 9, - }, - greaterSlick: { - id: 'greaterSlick', - label: 'greater slick', - price: 450, - level: 8, - }, - greaterWinged: { - id: 'greaterWinged', - label: 'greater winged', - price: 35000, - level: 19, - }, - invisibility: { - id: 'invisibility', - label: 'invisibility', - price: 500, - level: 8, - }, - majorShadow: { - id: 'majorShadow', - label: 'major shadow', - price: 14000, - level: 17, - }, - majorSlick: { - id: 'majorSlick', - label: 'major slick', - price: 9000, - level: 16, - }, - ready: { - id: 'ready', - label: 'ready', - price: 200, - level: 6, - }, - rockBraced: { - id: 'rockBraced', - label: 'rock-braced', - price: 3000, - level: 13, - }, - shadow: { - id: 'shadow', - label: 'shadow', - price: 55, - level: 3, - }, - sinisterKnight: { - id: 'sinisterKnight', - label: 'sinister knight', - price: 500, - level: 8, - }, - slick: { - id: 'slick', - label: 'slick', - price: 45, - level: 3, - }, - winged: { - id: 'winged', - label: 'winged', - price: 2500, - level: 13, - }, - }, - }, -}; -export type ITEM_RUNES = typeof ITEM_RUNES; diff --git a/src/module/loot-app/LootAppExternal.ts b/src/module/loot-app/LootAppExternal.ts deleted file mode 100644 index 36729be..0000000 --- a/src/module/loot-app/LootAppExternal.ts +++ /dev/null @@ -1,61 +0,0 @@ -/* Copyright 2020 Hooking et. al - * https://gitlab.com/hooking/foundry-vtt---pathfinder-2e/ - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -type ItemPlaceholder = any; - -interface Coins { - pp: number; - gp: number; - sp: number; - cp: number; -} - -function toCoins(denomination: string, value: number): Coins { - return { - pp: denomination === 'pp' ? value : 0, - gp: denomination === 'gp' ? value : 0, - sp: denomination === 'sp' ? value : 0, - cp: denomination === 'cp' ? value : 0, - }; -} - -function noCoins(): Coins { - return { - pp: 0, - gp: 0, - sp: 0, - cp: 0, - }; -} - -function combineCoins(first: Coins, second: Coins): Coins { - return { - pp: first.pp + second.pp, - gp: first.gp + second.gp, - sp: first.sp + second.sp, - cp: first.cp + second.cp, - }; -} - -export function calculateWealth(items: ItemPlaceholder[]): Coins { - return items - .filter((item) => item.type === 'treasure' && item?.data?.denomination?.value !== undefined && item?.data?.denomination?.value !== null) - .map((item) => { - const value = (item.data?.value?.value ?? 1) * (item.data?.quantity?.value ?? 1); - return toCoins(item.data.denomination.value, value); - }) - .reduce(combineCoins, noCoins()); -} diff --git a/src/module/loot-app/LootAppUtil.ts b/src/module/loot-app/LootAppUtil.ts deleted file mode 100644 index 5ea24bc..0000000 --- a/src/module/loot-app/LootAppUtil.ts +++ /dev/null @@ -1,108 +0,0 @@ -/* - * Copyright 2021 Andrew Cuccinello - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -export async function GetRollableTables() { - const pack = game.packs.get('pf2e.rollable-tables') as any; - const tables = (await pack.getContent()) as RollTable[]; - return { pack, tables }; -} - -export async function GetItemFromCollection(collectionId: string, itemId: string) { - const pack = (await game.packs.get(collectionId)) as any; - // @ts-ignore - return await pack.get(itemId); -} - -export async function GetTreasureTables() { - const { pack, tables } = await GetRollableTables(); - - const find = (name: string) => { - return tables.find((table) => table.name === name); - }; - - const value = (base: number, denomination: 'sp' | 'gp') => { - return `${base}${denomination}-${4 * base}${denomination}`; - }; - - return [ - { - table: find('Lesser Semiprecious Stones'), - value: value(5, 'sp'), - }, - { - table: find('Moderate Semiprecious Stones'), - value: value(25, 'sp'), - }, - { - table: find('Greater Semiprecious Stones'), - value: value(5, 'gp'), - }, - { - table: find('Lesser Precious Stones'), - value: value(50, 'gp'), - }, - { - table: find('Moderate Precious Stones'), - value: value(100, 'gp'), - }, - { - table: find('Minor Art Object'), - value: value(1, 'gp'), - }, - { - table: find('Lesser Art Object'), - value: value(10, 'gp'), - }, - { - table: find('Moderate Art Object'), - value: value(25, 'gp'), - }, - { - table: find('Greater Art Object'), - value: value(250, 'gp'), - }, - { - table: find('Major Art Object'), - value: value(1000, 'gp'), - }, - ]; -} - -export async function GetMagicItemTables(searchName: string) { - let { pack, tables } = await GetRollableTables(); - tables = tables.filter((table) => table.name?.includes(searchName)); - - const sortRegex = /[0-9]+/; - - tables.sort((a, b) => { - let an = 0; - let bn = 0; - - const ar = sortRegex.exec(a.name as string); - const br = sortRegex.exec(b.name as string); - - if (ar !== null) { - an = parseInt(ar[0]); - } - if (br !== null) { - bn = parseInt(br[0]); - } - - return an - bn; - }); - - return tables; -} diff --git a/src/module/macros/distribute-hero-points.ts b/src/module/macros/distribute-hero-points.ts index f611e0f..e79e7a7 100644 --- a/src/module/macros/distribute-hero-points.ts +++ b/src/module/macros/distribute-hero-points.ts @@ -14,8 +14,8 @@ * limitations under the License. */ -import ModuleSettings from '../../../FVTT-Common/src/module/settings-app/ModuleSettings'; import { MAX_HERO_POINTS } from '../Setup'; +import ModuleSettings from '../../../FVTT-Common/src/module/ModuleSettings'; export async function distributeHeroPoints(amount: number) { const selected = (canvas as Canvas).tokens?.controlled as Token[]; diff --git a/src/templates/loot-app/LootApp.html b/src/templates/loot-app/LootApp.html deleted file mode 100644 index dbd6094..0000000 --- a/src/templates/loot-app/LootApp.html +++ /dev/null @@ -1,24 +0,0 @@ -
- -
- {{#if owner}} -

- -

- {{else}} -

{{actor.name}}

- {{/if}} -
- {{data.lootSheetType}} -
-
- {{#if user.isGM}} - - {{else}} - {{> systems/pf2e/templates/actors/loot/sidebar.html}} - {{/if}} - - {{> systems/pf2e/templates/actors/loot/inventory.html}} -
diff --git a/src/templates/loot-app/LootAppConsumables.html b/src/templates/loot-app/LootAppConsumables.html deleted file mode 100644 index 36be251..0000000 --- a/src/templates/loot-app/LootAppConsumables.html +++ /dev/null @@ -1,9 +0,0 @@ -{{#each consumablesTables as |table|}} -
- -
- - -
-
-{{/each}} \ No newline at end of file diff --git a/src/templates/loot-app/LootAppMagicItems.html b/src/templates/loot-app/LootAppMagicItems.html deleted file mode 100644 index f7e9f71..0000000 --- a/src/templates/loot-app/LootAppMagicItems.html +++ /dev/null @@ -1,9 +0,0 @@ -{{#each magicItemTables as |table|}} -
- -
- - -
-
-{{/each}} \ No newline at end of file diff --git a/src/templates/loot-app/LootAppScrolls.html b/src/templates/loot-app/LootAppScrolls.html deleted file mode 100644 index 2f6df22..0000000 --- a/src/templates/loot-app/LootAppScrolls.html +++ /dev/null @@ -1 +0,0 @@ -

Not Yet Functional

\ No newline at end of file diff --git a/src/templates/loot-app/LootAppSidebar.html b/src/templates/loot-app/LootAppSidebar.html deleted file mode 100644 index d1ebf93..0000000 --- a/src/templates/loot-app/LootAppSidebar.html +++ /dev/null @@ -1,87 +0,0 @@ - - - - -
-
-
- -
- {{#if user.isGM}} - {{#if isLoot}} -
- - - -
- {{/if}} - - -

{{localize "PF2E.loot.GMSettings"}}

-
-
-

- - {{localize "PF2E.loot.SheetType"}} - -

-
-

- {{localize "PF2E.loot.LootLabel"}}: {{localize "PF2E.loot.LootDescription"}} -

-

- {{localize "PF2E.loot.MerchantLabel"}}: {{localize "PF2E.loot.MerchantDescription"}} -

-
-
- -
-
-
- {{/if}} -
-
- {{> modules/pf2e-toolbox/templates/loot-app/LootAppTreasure.html }} -
-
- {{> modules/pf2e-toolbox/templates/loot-app/LootAppMagicItems.html }} -
-
- {{> modules/pf2e-toolbox/templates/loot-app/LootAppConsumables.html }} -
-
- {{> modules/pf2e-toolbox/templates/loot-app/LootAppScrolls.html }} -
-
- {{> modules/pf2e-toolbox/templates/loot-app/create/CreateTab.html }} -
-
\ No newline at end of file diff --git a/src/templates/loot-app/LootAppTreasure.html b/src/templates/loot-app/LootAppTreasure.html deleted file mode 100644 index 1ad333e..0000000 --- a/src/templates/loot-app/LootAppTreasure.html +++ /dev/null @@ -1,10 +0,0 @@ -{{#each treasureTables as |entry|}} -
- -
- - - -
-
-{{/each}} \ No newline at end of file diff --git a/src/templates/loot-app/create/CreateArmor.html b/src/templates/loot-app/create/CreateArmor.html deleted file mode 100644 index 8cad8cc..0000000 --- a/src/templates/loot-app/create/CreateArmor.html +++ /dev/null @@ -1,3 +0,0 @@ -

Create Armor

- -{{> modules/pf2e-toolbox/templates/loot-app/create/CreateShared.html}} \ No newline at end of file diff --git a/src/templates/loot-app/create/CreateShared.html b/src/templates/loot-app/create/CreateShared.html deleted file mode 100644 index 47a4142..0000000 --- a/src/templates/loot-app/create/CreateShared.html +++ /dev/null @@ -1,111 +0,0 @@ -{{> modules/pf2e-toolbox/templates/loot-app/create/SelectRow.html name="baseItem" - label="Base Item" value=create.baseItem options=create.baseItemOptions}} - -{{#if create.baseItem}} - {{> modules/pf2e-toolbox/templates/loot-app/create/RuneStats.html level=create.baseItemLevel price=create.baseItemPrice}} -{{/if}} - -

Material

-{{> modules/pf2e-toolbox/templates/loot-app/create/SelectRow.html name="material" - label="Material" value=create.material options=create.materialOptions}} - -{{> modules/pf2e-toolbox/templates/loot-app/create/SelectRow.html name="grade" - label="Grade" value=create.grade options=create.gradeOptions}} - -{{#if create.material}} -

- - {{create.materialHardness}} - {{create.materialHp}} - {{create.materialBt}} - - - +{{commas create.materialPrice}} gp/bulk - -

-{{/if}} - -

Runes

-{{> modules/pf2e-toolbox/templates/loot-app/create/SelectRow.html name="potency" - label="Potency" value=create.potency options=create.potencyOptions}} - -{{#ifgt create.potency.nId 0}} - {{> modules/pf2e-toolbox/templates/loot-app/create/RuneStats.html level=create.potencyLevel price=create.potencyPrice}} -{{/ifgt}} - -{{#ifgt create.potency.nId 0}} - {{> modules/pf2e-toolbox/templates/loot-app/create/SelectRow.html name="fundamental" - label="Fundamental" value=create.fundamental options=create.fundamentalOptions}} - {{#ifgt create.fundamental.nId 0}} - {{> modules/pf2e-toolbox/templates/loot-app/create/RuneStats.html level=create.fundamentalLevel price=create.fundamentalPrice}} - {{/ifgt}} - - {{> modules/pf2e-toolbox/templates/loot-app/create/SelectRow.html name="property1" - label="Property 1" value=create.property1 options=create.propertyOptions}} - {{#if create.property1}} - {{> modules/pf2e-toolbox/templates/loot-app/create/RuneStats.html level=create.property1Level price=create.property1Price}} - {{/if}} -{{/ifgt}} - -{{#ifgt create.potency.nId 1}} - {{> modules/pf2e-toolbox/templates/loot-app/create/SelectRow.html name="property2" - label="Property 2" value=create.property2 options=create.propertyOptions}} - {{#if create.property2}} - {{> modules/pf2e-toolbox/templates/loot-app/create/RuneStats.html level=create.property2Level price=create.property2Price}} - {{/if}} -{{/ifgt}} - -{{#ifgt create.potency.nId 2}} - {{> modules/pf2e-toolbox/templates/loot-app/create/SelectRow.html name="property3" - label="Property 3" value=create.property3 options=create.propertyOptions}} - {{#if create.property3}} - {{> modules/pf2e-toolbox/templates/loot-app/create/RuneStats.html level=create.property3Level price=create.property3Price}} - {{/if}} -{{/ifgt}} - -
- -

Final Stats

-

- {{#if create.potency}} - {{#ifgt create.potency.nId 0}} - +{{create.potency.nId}} - {{/ifgt}} - - {{#ifgt create.fundamental.nId 0}} - {{create.fundamental.label}} - {{/ifgt}} - {{#if create.property1}} - {{create.property1.label}} - {{/if}} - {{#if create.property2}} - {{create.property2.label}} - {{/if}} - {{#if create.property3}} - {{create.property3.label}} - {{/if}} - - {{/if}} - {{create.baseItem.name}} -

- -

- {{create.itemRarity}} -

- -

- - {{create.itemLevel}} - - - {{#ifeq create.itemLevel 25}} - - {{else}} - {{commas create.itemPrice}} gp - {{/ifeq}} - -

- -
- -
\ No newline at end of file diff --git a/src/templates/loot-app/create/CreateTab.html b/src/templates/loot-app/create/CreateTab.html deleted file mode 100644 index 041b2bb..0000000 --- a/src/templates/loot-app/create/CreateTab.html +++ /dev/null @@ -1 +0,0 @@ -

The weapon/armor creator has been disabled due to actor-breaking bugs. It is currently being re-written and improved.

\ No newline at end of file diff --git a/src/templates/loot-app/create/CreateWeapon.html b/src/templates/loot-app/create/CreateWeapon.html deleted file mode 100644 index aa8f5bf..0000000 --- a/src/templates/loot-app/create/CreateWeapon.html +++ /dev/null @@ -1,3 +0,0 @@ -

Create Weapon

- -{{> modules/pf2e-toolbox/templates/loot-app/create/CreateShared.html}} \ No newline at end of file diff --git a/src/templates/loot-app/create/RuneStats.html b/src/templates/loot-app/create/RuneStats.html deleted file mode 100644 index b303221..0000000 --- a/src/templates/loot-app/create/RuneStats.html +++ /dev/null @@ -1,10 +0,0 @@ -

- {{#ifgt level 0}} - - {{level}} - - {{/ifgt}} - - +{{commas price}} gp - -

\ No newline at end of file diff --git a/src/templates/loot-app/create/SelectRow.html b/src/templates/loot-app/create/SelectRow.html deleted file mode 100644 index 6de1755..0000000 --- a/src/templates/loot-app/create/SelectRow.html +++ /dev/null @@ -1,11 +0,0 @@ -
- - - -
\ No newline at end of file