Compare commits

..

194 Commits

Author SHA1 Message Date
Matheus Clemente 0c5543fd89 Add Japanese class list 2024-03-28 18:08:18 -03:00
Matheus Clemente 9ddec1cbdb Update compendium-browser.js 2024-03-04 18:04:09 -03:00
Matheus Clemente dfa10b9f92 Improve class filtering
Related to #9
2024-03-04 17:46:24 -03:00
Matheus Clemente 4837213b89 Update settings.js 2024-03-04 17:20:12 -03:00
Matheus Clemente 63c5c7b8cf Update compendium-browser.js 2024-03-04 17:19:33 -03:00
Matheus Clemente 3380e77344 Improve compendium visibility settings
Related to #9.
2024-03-04 17:19:20 -03:00
Matheus Clemente d02e5eec4e Error handling for sorting
Related to #9.
2024-03-01 20:03:10 -03:00
Matheus Clemente 03853f55b9 Update dnd5e.js 2024-03-01 20:02:59 -03:00
Matheus Clemente 411c92a394 Fix filters 2024-02-28 15:54:44 -03:00
Matheus Clemente 4f5533d1f4 simplify sorting 2024-02-28 15:22:35 -03:00
Matheus Clemente b1aa359768 Update compendium-browser.js 2024-02-27 21:13:33 -03:00
Matheus Clemente bf91850a6f Update compendium-browser.js 2024-02-27 21:08:40 -03:00
Matheus Clemente 17e034bc75 remove copySearchToClipboard 2024-02-27 21:08:36 -03:00
Matheus Clemente cfb0725717 Update compendium-browser.js 2024-02-27 21:07:16 -03:00
Matheus Clemente 373bca7663 Update compendium-browser.js 2024-02-27 21:03:56 -03:00
Matheus Clemente 626454c411 Update compendium-browser.js 2024-02-26 19:57:08 -03:00
Matheus Clemente f84cb65f9b Update compendium-browser.js
Fix #8
2024-02-26 19:23:12 -03:00
Matheus Clemente 095a2aff4b Update filter-container.html 2024-02-26 19:10:03 -03:00
Matheus Clemente d603273d83 Update compendium-browser.js 2024-02-26 19:10:01 -03:00
Matheus Clemente 7c236bdc41 Improve Class item support
Fix #7.
2024-02-26 19:09:29 -03:00
Matheus Clemente baabb01011 Update module.json 2024-02-24 17:02:21 -03:00
Matheus Clemente cbbd323eeb Update compendium-browser.js 2024-02-24 16:08:08 -03:00
Matheus Clemente 4a821e2419 Update compendium-browser.js 2024-02-24 16:02:48 -03:00
Matheus Clemente f007e5789e Update module.json
Fix #5.
2024-02-11 15:55:03 -03:00
Matheus Clemente 650c42157c Update compendium-browser.js
Fix #4
2024-02-11 01:55:56 -03:00
Matheus Clemente 378818672b fix for dnd5e 3.0 2024-02-02 02:21:43 -03:00
Matheus Clemente 6fc06c7be2
Merge pull request #2 from ZoltanTheDM/features_branch_1
Races and Buttons
2023-12-19 03:14:18 -03:00
Zoltan The DM df7168f49c fixed lint error 2023-12-06 17:56:39 -08:00
Zoltan The DM 59bf58eac9 don't you hate it when you forget one character? 2023-11-30 15:20:23 -08:00
Zoltan The DM 7efe782bc6 big oops on using getter functions 2023-11-30 15:15:54 -08:00
Zoltan The DM 2f0f01b5a9 adds some nice clickable banners in case there are missing sections in the TidySheets 2023-11-30 15:08:20 -08:00
Zoltan The DM a54239a4f5 Adds a new clickable banner when missing 2023-11-29 16:50:23 -08:00
Zoltan The DM 8043efcf4a added options to the config 2023-11-17 14:28:06 -08:00
Zoltan The DM c01fe515d1 added a bunch of extra buttons to sheets for easy access to compendium browser 2023-11-17 13:48:25 -08:00
Zoltan The DM 52f1bfa089 added race to the list of filterables 2023-11-17 10:30:10 -08:00
Zoltan The DM d417d2887a fixed issue with renderWith not working 2023-11-17 10:16:56 -08:00
Matheus Clemente 2ee47cabb8 Update compendium-browser.js 2023-11-14 03:21:14 -03:00
Matheus Clemente d7544c09c4 Update compendium-browser.js 2023-11-14 03:20:45 -03:00
Matheus Clemente 514cb593ab Refactoring 2 2023-11-13 17:11:08 -03:00
Matheus Clemente c7189e2a99 Refactoring 2023-11-13 17:10:44 -03:00
Matheus Clemente c7e14e18bd Remove unused class 2023-11-13 16:48:33 -03:00
Matheus Clemente 5b5c067879 Add rarity strings 2023-11-13 16:48:21 -03:00
Matheus Clemente 2229aa9442 Update dnd5e.js 2023-11-12 03:20:53 -03:00
Matheus Clemente e335544bf6 Update compendium-browser.js 2023-11-12 03:11:53 -03:00
Matheus Clemente ef6fa264e3 Update dnd5e.js 2023-11-12 03:11:39 -03:00
Matheus Clemente 7359c359c9 Update compendium-browser.js 2023-11-12 02:24:07 -03:00
Matheus Clemente 8f221d8233 Update README.md 2023-11-12 02:21:04 -03:00
Matheus Clemente 3ae0c170f5 Update README.md 2023-11-12 02:15:03 -03:00
Matheus Clemente 18e7cfc3ed Update README.md 2023-11-12 02:14:50 -03:00
Matheus Clemente b607974d6f Update compendium-browser.js 2023-11-09 23:58:10 -03:00
Matheus Clemente 54e30791cc Revert "Remove code duplication"
This reverts commit 83a36634ca.
2023-11-09 18:24:57 -03:00
Matheus Clemente 83a36634ca Remove code duplication 2023-11-09 18:24:46 -03:00
Matheus Clemente 1ab7b499ab Update CHANGELOG.md 2023-11-09 14:59:23 -03:00
Matheus Clemente ca1f629151 Update compendium-browser.js 2023-11-09 14:50:57 -03:00
Matheus Clemente 8a8748e98c Remove fetching 2023-11-09 14:50:13 -03:00
Matheus Clemente 5a1c2239bd Update compendium-browser.js 2023-11-09 14:35:05 -03:00
Matheus Clemente 24c6885ad7 improve sorting 2 2023-11-09 14:33:06 -03:00
Matheus Clemente e7170f166a improve sorting 2023-11-09 14:29:34 -03:00
Matheus Clemente e0841dbc3b Linting 2023-11-09 14:29:24 -03:00
Matheus Clemente 6fb2a40216 Add dev tools 2023-11-09 14:14:29 -03:00
Matheus Clemente 0c2add7454 Move files 2 2023-11-09 14:04:11 -03:00
Matheus Clemente 2512b21ff2 Move files 2023-11-09 14:02:24 -03:00
Matheus Clemente 43240d02c7 Update compendium-browser.js 2023-11-09 13:42:01 -03:00
Matheus Clemente a04f8853b9 Update compendium-browser.css 2023-11-08 18:11:54 -03:00
Matheus Clemente 100dafc735 Update compendium-browser.less 2023-11-08 18:10:32 -03:00
Matheus Clemente bdb92d2388 Styling changes 2023-11-08 18:04:17 -03:00
Matheus Clemente 4249472cb5 Update localization 2023-11-08 18:04:10 -03:00
Matheus Clemente 2c65d1449c Update compendium-browser.js 2023-11-08 18:04:00 -03:00
Matheus Clemente 4eb3821a8e Update compendium-browser.css 2023-11-08 17:39:54 -03:00
Matheus Clemente 22a01aad5d Fix refresh 2023-11-08 17:24:09 -03:00
Matheus Clemente fcada213a2 Update en.json 2023-11-08 17:24:04 -03:00
Matheus Clemente 7983150350 Update Loading bar 2023-11-08 16:36:04 -03:00
Matheus Clemente eeffb9cba6 Add filter values sorting 2023-11-08 16:35:39 -03:00
Matheus Clemente 7f233cff5e Update compendium-browser.js 2023-11-08 16:34:54 -03:00
Matheus Clemente 459a0aab23 Refactoring 2023-11-08 16:34:25 -03:00
Matheus Clemente 327068c7e9 Remove version-specific logic 2023-11-08 14:54:09 -03:00
Matheus Clemente 8bf2bbfae2 Update templates 2023-11-08 14:53:51 -03:00
Matheus Clemente aa21882c16 Update module.json 2023-11-08 14:53:27 -03:00
Matheus Clemente 63758b9d27 Formatting 2023-11-08 00:43:18 -03:00
Matheus Clemente d8fb0eadca Update spell-browser-list.html 2023-11-08 00:35:07 -03:00
Matheus Clemente 980be2c7e6 Fix actor images 2023-11-08 00:22:13 -03:00
Matheus Clemente 9c095f3091 Visual improvements 2023-11-08 00:22:06 -03:00
Matheus Clemente 10b76040a1 Prettier formatting 3 2023-11-08 00:21:34 -03:00
Matheus Clemente f42ba3da33 Prettier formatting 2 2023-11-08 00:08:35 -03:00
Matheus Clemente 2c267d0c86 Prettier formatting 2023-11-08 00:03:55 -03:00
Zoltan the DM d52bf98bb4 Merge branch 'master' into mergable 2023-10-20 17:13:05 -07:00
Zoltan the DM d7f3159efa Merge remote-tracking branch 'lofd/master' into mergable 2023-10-20 17:11:07 -07:00
Zoltan the DM 0b10037449 Updated to fix some issues with version 11 2023-10-20 15:49:21 -07:00
ZoltanTheDM 7fc48e2771
Good enough for a new version (#56)
* fixed pt-br translation and extra string identifiers

Fixed some grammatical errors on the Brazilian Portuguese translation and added a few string identifiers to expand the translation of this module.

* added the additional fields to the other translations

* added some filters for the new dnd5e item types

* renderable and searchable from a function and button on the character sheet

* oops was only looking at the active tab on Tidy Sheet

* minor mistakes in merge

* using more names and words from DND5e language file

* added filter for backgrounds

* fixed item rarity filter in Foundty 10+

* updated readme

* format and link issues

---------

Co-authored-by: Eduardo Freire <edufc.rj@gmail.com>
2023-03-28 14:32:06 -07:00
Zoltan the DM 83a6047769 Merge branch 'master' into release 2023-03-14 17:10:00 -07:00
Zoltan the DM 6b4b3f527c format and link issues 2023-03-14 17:08:59 -07:00
Zoltan the DM aa3c7a4259 updated target 2023-03-14 17:03:50 -07:00
Zoltan the DM 922ffa6a87 Merge branch 'master' into release 2023-03-14 17:02:12 -07:00
Zoltan the DM 395d9226f6 updated readme 2023-03-14 17:01:57 -07:00
Zoltan the DM a0e7e319c6 fixed item rarity filter in Foundty 10+ 2023-03-14 16:48:07 -07:00
Zoltan the DM 3ad4f4b78f Merge branch 'master' into release 2023-03-14 16:33:25 -07:00
Zoltan the DM effbdbe5b9 added filter for backgrounds 2023-03-14 16:32:50 -07:00
Zoltan the DM 52a95a4e17 Merge branch 'master' into release 2023-03-14 16:23:40 -07:00
Zoltan the DM adda90c282 using more names and words from DND5e language file 2023-03-14 16:23:18 -07:00
Zoltan the DM 073869d18a added a new releases branch so anyone can use this 2023-03-08 13:12:56 -08:00
Zoltan the DM dc5dd51574 minor mistakes in merge 2023-02-10 10:05:15 -08:00
Zoltan the DM 0812d2efcc Merge branch 'master' of https://github.com/eduardopato41/compendium-browser into add-other-changes 2023-02-10 09:46:46 -08:00
Zoltan the DM b5f82115bb oops was only looking at the active tab on Tidy Sheet 2023-02-09 21:52:52 -08:00
Zoltan the DM 9a5e6a7d27 renderable and searchable from a function and button on the character sheet 2023-02-09 00:31:57 -08:00
Zoltan the DM 165445df29 added some filters for the new dnd5e item types 2023-02-03 20:46:26 -08:00
Eduardo Freire 7b6e590618 added the additional fields to the other translations 2022-09-24 15:17:44 -03:00
Eduardo Freire 126a264d87 fixed pt-br translation and extra string identifiers
Fixed some grammatical errors on the Brazilian Portuguese translation and added a few string identifiers to expand the translation of this module.
2022-09-23 17:42:27 -03:00
joevaughan d4181d347e
Fixes for issue #41 and #43 (#44)
Co-authored-by: Joe Vaughan <Joe.Vaughan@xoserve.com>
2022-09-23 12:05:07 -07:00
Pipper Publishing 8c6546a97d 0.8.1 16-Sep-2022
- Updated description to reflect Foundry v10 support
2022-09-16 14:13:24 +12:00
joevaughan fd0c903be3
Foundry V10 compatibility (#40)
* Foundry V10 compatibility

* bumped number for download zip

* Fixes for v9 and set minimum compat to v9.266

Co-authored-by: Joe Vaughan <Joe.Vaughan@xoserve.com>
2022-09-14 15:50:08 -04:00
opus1217 2941513636 0.7.2d 5-Jan-2022
Fix badly-formed NPCs if necessary
2022-01-05 16:09:02 -08:00
Spetzel c1ac2b0722
Update README.md 2022-01-04 17:40:55 -08:00
Spetzel 1b198a02ff
Update README.md 2022-01-04 17:40:20 -08:00
opus1217 755308e83c 0.7.2b 4-Jan-2022
- Merge PR #33 (improved NPC search performance) - thanks kyleady
- Fixed #29,#30,#31: Problems running with Foundry v9
- Fixed #28: Problems sorting by magical rarity
- change message to Loading... while still loading.
2022-01-04 17:39:05 -08:00
kyleady 72227b1a4f
Use .getIndex() to fetch minimal information for filtering NPCs (#33)
Thanks for the update!
2022-01-04 16:07:04 -08:00
opus1217 62c64e432f 0.7.2 1-Jan-2022
Remove deprecated variables
Check for isFoundryv8Plus
2022-01-01 21:27:33 -08:00
Pipper Publishing d789f150ab v0.7.1a 12-Sep-2021
Revved module.json
2021-09-12 14:01:48 +12:00
Spetzel e486f3d3cf
Update Patchnotes.md 2021-09-11 18:47:31 -07:00
Pipper Publishing 78bc52535d v0.7.1 12-Sep-2021
Fixed Issue #25 Compendium Browser doesn't show

compendium-browser.js
- initSettings(): Check that settings.loadedSpellCompendium and settings.loadedNpcCompendium exist
2021-09-12 13:26:38 +12:00
Pipper Publishing 4c52de66a6 Merge branch 'master' of https://github.com/League-of-Foundry-Developers/compendium-browser 2021-09-10 09:42:32 +12:00
Pipper Publishing 41bc3738f6 v0.7.1 10-Sep-2021
- Merged PR #26
- Revved CMPBrowser structure (was at 0.4.5)
2021-09-10 09:42:28 +12:00
John McGinn a59ce55023
Adding sorcerer & wizard to tasha's caustic brew (#26) 2021-09-07 19:01:26 -07:00
Pipper Publishing de6b59cf82 v0.7.0b 8-Sep-2021
- Patchnotes re fixing Issue #7 as well
2021-09-08 12:57:01 +12:00
Pipper Publishing a0277c9b86 v0.7.0 7-Sep-2021
-Merged PR #24
- Fixed: Support for CompendiumCollection#getContent will be removed in 0.9.0. League-of-Foundry-Developers/compendium-browser#19
- Revved versions and updated Patch notes
2021-09-07 15:00:11 +12:00
ZoltanTheDM ef024fbb89
Performance and 0.9.0 prep (#24)
* significant performance improvements

* added notes to change log

* spelling mistake 1

* spelling mistake 2
2021-09-06 19:34:03 -07:00
Spetzel 71d9fd7584
Update README.md 2021-09-04 20:44:39 -07:00
Pipper Publishing c6ef646da2 v0.6.0e 5-Sep-2021
- Attribution for Spanish and German translations
- Updates for Patchnotes and README
2021-09-05 15:40:16 +12:00
Pipper Publishing 9d72f1bdac v0.6.0d 5-Sep-2021 2021-09-05 15:27:26 +12:00
Pipper Publishing 45f88c9436 v0.6.0d 5-Sep-2021
- Manually merged PR #3 (Spanish and German translations)

module.json
- Reference language additions and give attribution

de.json, es.json: ADDED
2021-09-05 15:26:28 +12:00
Pipper Publishing 686e9df31c 0.6.0c 5-Sep-2021 Update Patchnodes.md for PR merges 2021-09-05 13:04:12 +12:00
Pipper Publishing d74183149a 0.6.0b 5-Sep-2021
-Modified description for merges: Tasha's classes
2021-09-05 12:36:22 +12:00
Spetzel 405dbb799f
Merge pull request #14 from Tupsi/master
Added bard spells from TCE (actually Bard spells added as Optional Class Features)
2021-09-04 17:34:15 -07:00
Spetzel 998d9f6613
Merge branch 'master' into master 2021-09-04 17:33:31 -07:00
Pipper Publishing d48c572ffe Merge branch 'master' of https://github.com/League-of-Foundry-Developers/compendium-browser 2021-09-05 12:03:38 +12:00
Spetzel 64811db939
Merge pull request #8 from jeremyregnerus/Rime-and-Tashas
Updates new spells and classes
2021-09-04 17:03:06 -07:00
Pipper Publishing f7fa4de8d9 0.6.0 5-Sep-2021
- Merge PRs for languages and performance improvements
2021-09-05 09:38:12 +12:00
Spetzel 0a4a6cfc2f
Fix manifest.json path 2021-06-12 20:13:35 -07:00
opus1217 c5b5cd0dcd Merge branch 'master' of https://github.com/League-of-Foundry-Developers/compendium-browser into master 2021-06-12 20:09:56 -07:00
opus1217 0f6fb758cb 0.5.0b 12-Jun-2021
Updated module.json description
2021-06-12 20:09:51 -07:00
Spetzel e19f824d94
Update README.md 2021-06-12 20:04:04 -07:00
opus1217 17529c9d78 0.5.0b 12-Jun-2021
Updated Pathnotes.md
2021-06-12 20:03:00 -07:00
opus1217 5e01bca499 0.5.0 12-Jun-2021
- Updated to use correct "latest" link
- Fixed: Issue https://github.com/League-of-Foundry-Developers/compendium-browser/issues/17 (structure had changed)

compendium-browser.js
- addNpcFilers(): Test for Foundry 0.8.x in which creature type is now data.details.type.value
2021-06-12 19:59:08 -07:00
Ugurtan 2e8987ddb4
updated with new bard spells from tasha's 2021-03-21 13:46:29 +01:00
Ugurtan 639a8e7b38
Updated with bard spells from tasha's 2021-03-21 13:31:38 +01:00
Spetzel b2a287fd5d
Updated description for 0.4.5 2021-03-17 12:15:20 -07:00
opus1217 fa852fdfd6 Merge branch 'master' of https://github.com/League-of-Foundry-Developers/compendium-browser into master 2021-03-17 12:11:25 -07:00
Spetzel 3bd1ba5f45
Update Patchnotes.md 2021-03-17 12:10:18 -07:00
Spetzel 0002c9559c
Reordered newest to old; added 0.4 updates 2021-03-17 12:08:51 -07:00
Spetzel 1b4a5098cc
Update README.md 2021-03-17 10:38:24 -07:00
opus1217 63e4e7832e 0.4.5b 15-Mar-2021
- Display tooltip over item/npc name with source compendium

*-browser-list.html
- Add title tooltip to the item/npc names
2021-03-15 13:45:45 -07:00
opus1217 f724d8fb4e 0.4.5 15-Mar-2021
Fixed; Issue #10 ( Spells from non-system compendium show up in items tab.)

compendium-browser.js
- loadAndFilterItems(): Refactor test on content to switch on tab (spells, feats, items) and if on item type
- getFilterResult() -> passesFilter()
2021-03-15 13:06:06 -07:00
Spetzel 280c0bcb44
Merge pull request #12 from League-of-Foundry-Developers/v0.3.1-spetzel2020
V0.3.1 spetzel2020
2021-03-12 14:06:39 -08:00
opus1217 a6502011e5 0.4.3c 12-Mar-2021
Updated module description with fixed bugs
2021-03-12 13:47:55 -08:00
opus1217 de541099c3 0.4.3 12-Mar-2021
Version to v0.4.3 for testing
2021-03-12 13:34:01 -08:00
opus1217 1679b50859 0.4.3b 11-Mar-2020
- Changed Reset Filters prompt to be consistent
- Fully fixed Issue #4 (filters still showing after reset)

compendium-browser.js
- Clear all filters to match displayed

*-browser.html
- Substitute more localization tags

template.html
- Fixed unlisted bug for content (repeated #if showSpellBrowser)

en.json
- Add localization for "Reset Filters" prompt
2021-03-11 18:26:51 -08:00
opus1217 d7d8e85e3c 0.4.3 11-Mar-2021
- Fixed: Error on dragging item from Compendium Browser #9
- Partially Fixed: Issue #4 (filter fields don't get cleared)
-- Is clearing on the current tab but getting out of sync otherwise on other tabs

compendium-browser.js:
- activateItemListListeners(): Remove spurious li.parents (wasn't being used anyway)
- activateListeners(): Add this.refreshList to say what tab we should get data for and then re-render
2021-03-11 17:32:07 -08:00
Jeremy Regnerus b1945af048
Updates new spells and classes
Includes new spells from Rime of the Frostmaiden and Tasha's Cauldron of everything. Also includes new Artificier spells.
2021-02-27 15:47:58 -05:00
Spetzel d64fb87a5f
Update README.md 2021-02-17 14:31:19 -08:00
opus1217 1aa555638f 0.4.2 17-Dec-2021
module.json: Updated Description to match new Lite behavior
2021-02-17 14:29:24 -08:00
Spetzel 56020bba22
Expand Installation and Summary 2021-02-17 14:17:51 -08:00
Spetzel d96a339991
Described new behavior and differentiation from old version 2021-02-17 14:11:54 -08:00
opus1217 4ddad55232 0.4.2f 16-Feb-2021
- Working with Loading and Maximum message at top
- Reset Filters is not resetting filter display

compendium-browser.js
- Change preload to maxLoaded and display a message to filter if you want more
- replaceList(): Pass updateLoading function (with max warning) to renderItemData

en.json
CMPBrowser.SETTING.Preload -> Maxload
CMPBrowser.LOADING.Message, .MaxLoaded: ADDED

*-browser.html
- Add messages line, convert to flexcol

*-browser-list.html
- Use same argument (listItems)

loading.html
- Message (including maximum if found)

compendium-browser.css
- Add .list-area styling consistent with flex
- Adjust max-width
- Remove ul setting of width
2021-02-16 20:39:39 -08:00
Pipper Publishing 0aeecb6963 0.4.2e 15-Feb-2021 2021-02-16 11:55:46 -08:00
Pipper Publishing 2ad8d26537 0.4.2d 15-Feb-2021
- Display the type of item being loaded

compendium-browser.js
- renderLoading(): ADDED
2021-02-15 18:49:06 -08:00
Pipper Publishing 9cf9eff45f 0.4.2c 15-Feb-2021
- Correct loading/reloading message

compendium-browser.js
- Correct Loading... message on initial tab, but not on tab switch
- replaceList(): Use new loading.html template

loading.html: ADDED
2021-02-15 16:47:48 -08:00
opus1217 9bb2bd90e1 0.4.2c 15-Feb-2021
Broke the reloading - need to check if there is only the loading message on a reload
2021-02-15 14:27:15 -08:00
opus1217 cdadb915ea 0.4.2b 15-Feb-2021
- Add Loading... message for NPCs
- Don't reload if tab already has data, unless you reset filters

compendium-browser.js
- replaceList(): Add options.force to force reload even if there's data (e.g. if you reset filters)
2021-02-15 14:14:45 -08:00
opus1217 3ff0a0fac5 0.4.2 15-Feb-2021
NPC initial load working and subsequent filtering/ordering

compendium-browser.js
- Fix NPCs to use loadAndFilterNpcs
loadAndFilterNpcs(): ADDED
- On settings changed, just do new render()
- decorateCompendiumEntry() -> decorateItem()

npc-browser.html
- Use correct css (cr vs cr-display etc)
- Simplify hidden filtering data fields

module.json
- Version bump
2021-02-15 13:50:14 -08:00
opus1217 0b9b72edff 0.4.1l 12-Feb-2021
Display static "Loading..." message the first time tab is shown
-> Want it with dynamic results and to not replace existing data

feat-browser.html, spell-browser.html
- Use items array on first load so that we pick up "Loading..." message
2021-02-12 12:14:37 -08:00
opus1217 86b15332fe 0.4.1k 12-Feb-2021
Auto-populates the visible tab (based on what is meant to be displayed)
- Needs a Loading... progress indicator in the data area + remember if data has been loaded already

compendium-browser.js
- afterRender(): Hook called after app is rendered to populate initial data
- _onChangeTab(): Override to load data in this tab when you switch tabs
- Move observer to be an instance property

en.json
- Add tab name tags

template.html
- Use tab name tags
2021-02-12 10:53:58 -08:00
opus1217 558cd6c8d0 0.4.1j 12-Feb-2021
- Correct compactItem for feats and items required display items
- Rename itemType -> browserTab to differentiate candidate item's type from the tab it appears on (spell, feat/class, item, NPC)
 - Fixed: Was calling the wrong sort for feat and NPC
2021-02-12 08:53:29 -08:00
opus1217 c9b6a751ad 0.4.1i 11-Feb-2021
All tabs now showing values (although missing correct decorations)

compendium-browser.js
- loadAndFilterItems(): test for item5e was skipping items called loot, equipment etc.
2021-02-11 22:13:17 -08:00
opus1217 4fb315bed3 0.4.1h 11-Feb-2021
Feats seem to be working (missing fields)
Items now showing
NPCs operating erratically

compendium-browser.js
- Add the partials for npc, feat, item and the backing code

*-browser-list.html: ADDED
(partials for changing data)
2021-02-11 20:47:43 -08:00
opus1217 249f558a2a 0.4.1g 11-Feb-2021
Generalize the spell list reload and confirm spells still working

compendium-browser.js
- triggerSortSpells() -> triggerSort()
- replaceSpells() -> replaceList()
- renderSpellData() -> renderItemData()
- Remove list/subjects settings and replace with this.replaceList() throughout
2021-02-11 18:05:08 -08:00
opus1217 f1a050d2ad 0.4.1f 11-Feb-2021
Initial spell loading working, without preload limit
2021-02-11 17:23:49 -08:00
opus1217 4bee393f39 0.4.1e 11-Feb-2021
-Spell panel working except for initial and sorting

compendium-browser.js
- Don't save the filter data (which is most of the memory) and remove the preload limit; instead just save the minimal amount of data
- loadAndFilterItems(): Only load the tab you're on - for now just spells
-- store compactItems instead of whole decoratedItem (which was used for filtering)
-activateListeners(): Split out activateItemListListeners() so we can call them when we reload

spell-browser.html
2021-02-11 16:40:18 -08:00
opus1217 07d3d378f6 0.4.1d 9-Feb-2021
Fixed: img observer on replaced spellData

compendium-browser.js
- replaceSpells(): Put image observer on correct replacement
2021-02-09 21:53:05 -08:00
opus1217 991e116d68 0.4.1d 9-Feb-2021
Basic POC for on-demand query from Compendia
for spell-filters only
- Other filters are broken right now

spell-browser.html
- Split out spell-browser-list.html so we can render this separately with refreshed data

compendium-browser.js
- replaceSPells(), renderSpellData(): ADDED
- Fixed: loadAndFilterItems(), loadItems(): await checkListsLoaded() or we get a null error
- activateListeners(): Use replaceSpells() instead of filterElements or full render
2021-02-09 21:42:50 -08:00
opus1217 0353c307a4 0.4.1c 9-Feb-2021 Working
- Shows initial results, limited to PRELOAD

compendium-browser.js
- loadAndFilterItems(): pass activeFilters
2021-02-09 14:37:44 -08:00
opus1217 ae4a163f88 0.4.1b 9-Feb-2021 NOT WORKING
Interim check-in with loadAndFilterItems

compendium-browser.js
- Call loadAndFilterItems instead of loadItems; filter as we go, limited by numToPreload
- Add VISIBLE_ROWS (not used)
- loadAndFillterItems(): ADDED
-decorateCompendiumEntry(): ADDED
- checkListsLoaded(): ADDED
- fix more eslint errors (===)
- change "compendiumBrowser" module ID to MODULE_NAME (="compendium-browser")
2021-02-09 10:21:12 -08:00
opus1217 24cfde1119 0.4.1 8-Feb-2021
Fixed: Issue #2: Was loading items twice (once as this.items, once as this.spells)

compendium-browser.js
- Add numToPreload (default 100, in Settings)
- loadItems(), loadNPCs() load "preload" number of spells, feats, items, NPCs each
- initialize(): Was setting this.spells and then setting this.items in getData()
-  Move load back to "ready" hook, but limit number loaded
- Added CMPBrowser constants
- Fixed minor eslint problems
- getData(): Cleaned up data initialization
2021-02-08 09:13:31 -08:00
Spetzel b2834a44c3
Spelling errors (Issue #1) 2021-02-08 08:58:53 -08:00
opus1217 5c3ed89b71 0.4.0 4-Feb-2021
- Defer spell/item and NPC loading until you use the Compendium Browser

compendium-browser.js
- Switch to not pre-loading the indexes, and instead do that at browsing time, to reduce server load and memory usage
- getData(): Check spellsLoaded, npcsLoaded
- loadItems(): Deprecated spellsLoading
- addSpellFilters(), addFeatFilters(), addItemFilters(), addNpcFilters(): Added just for easier reading
- Refactor some of the eslint warnings

module.json
- Version bump to 0.4.0
2021-02-04 18:50:25 -08:00
Felix 6927bd496a
Merge pull request #7 from rinnocenti/patch-2
Update module.json
2020-07-07 18:11:44 +02:00
Felix bcd2c6fad3
Merge pull request #6 from rinnocenti/patch-1
translate pt-BR
2020-07-07 18:11:32 +02:00
Renato Innocenti ba1289fa99
Update module.json 2020-07-07 12:38:00 -03:00
Renato Innocenti d5ce9e676a
translate pt-BR
translate portuguese Brazil
2020-06-27 02:14:53 -03:00
Felix 4a8c76a3af
Update Patchnotes.md 2020-06-12 18:33:32 +02:00
Felix 78ffcee69e
Add files via upload 2020-06-12 18:23:32 +02:00
Felix fdea01046d
Add files via upload 2020-06-12 18:16:39 +02:00
Felix ef2e6349b8
Add files via upload 2020-06-12 17:29:59 +02:00
Felix 8c076e313d
Update Patchnotes.md 2020-06-12 17:29:13 +02:00
Felix 03070dbb66
Update Patchnotes.md 2020-05-18 13:32:08 +02:00
Felix 7f9a113815
Add files via upload
fixed an issue that prevented the rendering of the Button to open the browser
2020-05-18 13:31:14 +02:00
56 changed files with 16535 additions and 2224 deletions

13
.editorconfig 100644
View File

@ -0,0 +1,13 @@
# SPDX-FileCopyrightText: 2022 Johannes Loher
#
# SPDX-License-Identifier: MIT
root = true
[*]
end_of_line = lf
insert_final_newline = true
indent_style = space
indent_size = 2
charset = utf-8
trim_trailing_whitespace = true

5
.eslintignore 100644
View File

@ -0,0 +1,5 @@
# SPDX-FileCopyrightText: 2022 Johannes Loher
#
# SPDX-License-Identifier: MIT
dist

185
.eslintrc.cjs 100644
View File

@ -0,0 +1,185 @@
// SPDX-FileCopyrightText: 2022 Johannes Loher
// SPDX-FileCopyrightText: 2022 David Archibald
//
// SPDX-License-Identifier: MIT
module.exports = {
parserOptions: {
ecmaVersion: 13,
extraFileExtensions: [".cjs", ".mjs"],
sourceType: "module",
},
env: {
browser: true,
es6: true,
jquery: true,
},
extends: ["eslint:recommended", "@typhonjs-fvtt/eslint-config-foundry.js/0.8.0"],
plugins: [],
globals: {
dnd5e: false
},
rules: {
"array-bracket-spacing": ["warn", "never"],
"array-callback-return": "warn",
"arrow-spacing": "warn",
"comma-dangle": ["warn", "only-multiline"],
"comma-style": "warn",
"computed-property-spacing": "warn",
"constructor-super": "error",
"default-param-last": "warn",
"dot-location": ["warn", "property"],
"eol-last": ["error", "always"],
eqeqeq: ["warn", "smart"],
"func-call-spacing": "warn",
"func-names": ["warn", "never"],
"getter-return": "warn",
"lines-between-class-members": "warn",
"new-parens": ["warn", "always"],
"no-alert": "warn",
"no-array-constructor": "warn",
"no-class-assign": "warn",
"no-compare-neg-zero": "warn",
"no-cond-assign": "warn",
"no-const-assign": "error",
"no-constant-condition": "warn",
"no-constructor-return": "warn",
"no-delete-var": "warn",
"no-dupe-args": "warn",
"no-dupe-class-members": "warn",
"no-dupe-keys": "warn",
"no-duplicate-case": "warn",
"no-duplicate-imports": ["warn", { includeExports: true }],
"no-empty": ["warn", { allowEmptyCatch: true }],
"no-empty-character-class": "warn",
"no-empty-pattern": "warn",
"no-func-assign": "warn",
"no-global-assign": "warn",
"no-implicit-coercion": ["warn", { allow: ["!!"] }],
"no-implied-eval": "warn",
"no-import-assign": "warn",
"no-invalid-regexp": "warn",
"no-irregular-whitespace": "warn",
"no-iterator": "warn",
"no-lone-blocks": "warn",
"no-lonely-if": "warn",
"no-misleading-character-class": "warn",
"no-mixed-operators": "warn",
"no-multi-str": "warn",
"no-multiple-empty-lines": ["warn", { max: 1 }],
"no-new-func": "warn",
"no-new-object": "warn",
"no-new-symbol": "warn",
"no-new-wrappers": "warn",
"no-nonoctal-decimal-escape": "warn",
"no-obj-calls": "warn",
"no-octal": "warn",
"no-octal-escape": "warn",
"no-promise-executor-return": "warn",
"no-proto": "warn",
"no-regex-spaces": "warn",
"no-script-url": "warn",
"no-self-assign": "warn",
"no-self-compare": "warn",
"no-setter-return": "warn",
"no-sequences": "warn",
"no-template-curly-in-string": "warn",
"no-this-before-super": "error",
"no-unexpected-multiline": "warn",
"no-unmodified-loop-condition": "warn",
"no-unneeded-ternary": "warn",
"no-unreachable": "warn",
"no-unreachable-loop": "warn",
"no-unsafe-negation": ["warn", { enforceForOrderingRelations: true }],
"no-unsafe-optional-chaining": ["warn", { disallowArithmeticOperators: true }],
"no-unused-expressions": "warn",
"no-useless-backreference": "warn",
"no-useless-call": "warn",
"no-useless-catch": "warn",
"no-useless-computed-key": ["warn", { enforceForClassMembers: true }],
"no-useless-concat": "warn",
"no-useless-constructor": "warn",
"no-useless-rename": "warn",
"no-useless-return": "warn",
"no-var": "warn",
"no-void": "warn",
"no-whitespace-before-property": "warn",
"prefer-numeric-literals": "warn",
"prefer-object-spread": "warn",
"prefer-regex-literals": "warn",
"prefer-spread": "warn",
"rest-spread-spacing": ["warn", "never"],
"semi-spacing": "warn",
"semi-style": ["warn", "last"],
"space-unary-ops": ["warn", { words: true, nonwords: false }],
"switch-colon-spacing": "warn",
"symbol-description": "warn",
"template-curly-spacing": ["warn", "never"],
"unicode-bom": ["warn", "never"],
"use-isnan": ["warn", { enforceForSwitchCase: true, enforceForIndexOf: true }],
"valid-typeof": ["warn", { requireStringLiterals: true }],
"wrap-iife": ["warn", "inside"],
"arrow-parens": ["warn", "always"],
"comma-spacing": "warn",
"dot-notation": "warn",
"key-spacing": "warn",
"keyword-spacing": ["warn", { overrides: { catch: { before: true, after: false } } }],
"max-len": [
"warn",
{
code: 120,
ignoreComments: true,
ignoreTrailingComments: true,
ignoreUrls: true,
ignoreStrings: true,
ignoreTemplateLiterals: true,
ignoreRegExpLiterals: true,
},
],
"no-extra-boolean-cast": ["warn", { enforceForLogicalOperands: true }],
"no-extra-semi": "warn",
"no-multi-spaces": ["warn", { ignoreEOLComments: true }],
"no-throw-literal": "error",
"no-trailing-spaces": "warn",
"no-useless-escape": "warn",
"no-unused-vars": ["warn", { args: "none" }],
"nonblock-statement-body-position": ["warn", "beside"],
"one-var": ["warn", "never"],
"operator-linebreak": [
"warn",
"before",
{
overrides: { "=": "after", "+=": "after", "-=": "after" },
},
],
"prefer-template": "warn",
"quote-props": ["warn", "as-needed", { keywords: false }],
quotes: ["warn", "double", { avoidEscape: true, allowTemplateLiterals: false }],
semi: "warn",
"space-before-blocks": ["warn", "always"],
"space-before-function-paren": [
"warn",
{
anonymous: "always",
named: "never",
asyncArrow: "always",
},
],
"spaced-comment": "warn",
},
overrides: [
{
files: ["./*.js", "./*.cjs", "./*.mjs"],
env: {
node: true,
},
},
],
};

65
.github/workflows/checks.yml vendored 100644
View File

@ -0,0 +1,65 @@
# SPDX-FileCopyrightText: 2022 Johannes Loher
#
# SPDX-License-Identifier: MIT
name: Checks
on:
- push
- pull_request
env:
node_version: 16
jobs:
lint:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v2
- name: Install node
uses: actions/setup-node@v2
with:
node-version: ${{ env.node_version }}
- name: Cache Node.js modules
uses: actions/cache@v2
with:
path: .npm
key: ${{ runner.OS }}-node-${{ hashFiles('**/package-lock.json') }}
restore-keys: |
${{ runner.OS }}-node-
${{ runner.OS }}-
- name: Install dependencies
run: npm ci --cache .npm --prefer-offline
- name: Lint
run: npm run lint
build:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v2
- name: Install node
uses: actions/setup-node@v2
with:
node-version: ${{ env.node_version }}
- name: Cache Node.js modules
uses: actions/cache@v2
with:
path: .npm
key: ${{ runner.OS }}-node-${{ hashFiles('**/package-lock.json') }}
restore-keys: |
${{ runner.OS }}-node-
${{ runner.OS }}-
- name: Install dependencies
run: npm ci --cache .npm --prefer-offline
- name: Build
run: npm run build

116
.github/workflows/release.yml vendored 100644
View File

@ -0,0 +1,116 @@
# SPDX-FileCopyrightText: 2022 Johannes Loher
#
# SPDX-License-Identifier: MIT
name: Release
on:
release:
types: [published]
env:
package_type: module
node_version: 16
jobs:
lint:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v2
- name: Install node
uses: actions/setup-node@v2
with:
node-version: ${{ env.node_version }}
- name: Cache Node.js modules
uses: actions/cache@v2
with:
path: .npm
key: ${{ runner.OS }}-node-${{ hashFiles('**/package-lock.json') }}
restore-keys: |
${{ runner.OS }}-node-
${{ runner.OS }}-
- name: Install dependencies
run: npm ci --cache .npm --prefer-offline
- name: Lint
run: npm run lint
build:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v2
- name: Install node
uses: actions/setup-node@v2
with:
node-version: ${{ env.node_version }}
- name: Cache Node.js modules
uses: actions/cache@v2
with:
path: .npm
key: ${{ runner.OS }}-node-${{ hashFiles('**/package-lock.json') }}
restore-keys: |
${{ runner.OS }}-node-
${{ runner.OS }}-
- name: Install dependencies
run: npm ci --cache .npm --prefer-offline
- name: Extract tag version number
id: get_version
uses: battila7/get-version-action@v2
- name: Substitute Manifest and Download Links For Versioned Ones
id: sub_manifest_link_version
uses: microsoft/variable-substitution@v1
with:
files: 'src/${{ env.package_type }}.json'
env:
version: ${{ steps.get_version.outputs.version-without-v }}
url: https://github.com/${{ github.repository }}
manifest: https://github.com/${{ github.repository }}/releases/latest/download/${{ env.package_type }}.json
download: https://github.com/${{ github.repository }}/releases/download/${{ github.event.release.tag_name }}/${{ env.package_type }}.zip
- name: Build
run: npm run build
- name: Archive production artifacts
uses: actions/upload-artifact@v2
with:
name: dist
path: dist
publish:
needs:
- lint
- build
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v2
- name: Download production artifacts for publication
uses: actions/download-artifact@v2
with:
name: dist
path: dist
- name: Create zip file
working-directory: ./dist
run: zip -r ../${{ env.package_type }}.zip .
- name: Create release
id: create_version_release
uses: ncipollo/release-action@v1
with:
allowUpdates: true
name: ${{ github.event.release.name }}
token: ${{ secrets.GITHUB_TOKEN }}
artifacts: './dist/${{ env.package_type }}.json, ./${{ env.package_type }}.zip'
body: ${{ github.event.release.body }}

32
.gitignore vendored 100644
View File

@ -0,0 +1,32 @@
# SPDX-FileCopyrightText: 2022 Johannes Loher
#
# SPDX-License-Identifier: MIT
# IDE
.idea/
.vs/
# Node Modules
node_modules/
npm-debug.log
# yarn2
.yarn/*
!.yarn/patches
!.yarn/releases
!.yarn/plugins
!.yarn/sdks
!.yarn/versions
.pnp.*
# Local configuration
foundryconfig.json
# Distribution files
dist
# ESLint
.eslintcache
# Junit results
junit.xml

5
.gulp.json 100644
View File

@ -0,0 +1,5 @@
{
"flags": {
"gulpfile": "gulpfile.mjs"
}
}

View File

@ -0,0 +1,4 @@
#!/usr/bin/env sh
. "$(dirname -- "$0")/_/husky.sh"
npx lint-staged

1
.nvmrc 100644
View File

@ -0,0 +1 @@
lts/*

8
.prettierignore 100644
View File

@ -0,0 +1,8 @@
# SPDX-FileCopyrightText: 2022 Johannes Loher
#
# SPDX-License-Identifier: MIT
dist
package-lock.json
.pnp.cjs
.pnp.js

9
.prettierrc.cjs 100644
View File

@ -0,0 +1,9 @@
// SPDX-FileCopyrightText: 2022 Johannes Loher
//
// SPDX-License-Identifier: MIT
module.exports = {
printWidth: 120,
tabWidth: 4,
useTabs: true,
};

84
CHANGELOG.md 100644
View File

@ -0,0 +1,84 @@
# 2.0.0
- Updated for V11.
- Small visual enhancements.
#0.9.0
- Button on character sheets for opening a search with class and spell level (works on default and TidySheet5e)
- added filters for subclasses and backgrounds [League-of-Foundry-Developers/compendium-browser#48](https://github.com/League-of-Foundry-Developers/compendium-browser/issues/48)
- Additional searches for sub-features
- Merged PR [League-of-Foundry-Developers/compendium-browser#45](https://github.com/League-of-Foundry-Developers/compendium-browser/pull/45)
- Used more DnD5e loaclization tags. Should be less work to translate, also defaults localization to tag name
- Fixed item rarity search in Foundry 10+ [League-of-Foundry-Developers/compendium-browser#54](https://github.com/League-of-Foundry-Developers/compendium-browser/issues/54)
#0.8.2
- Fixed Class searching for spells - issue: #43
- Fixed Drag-and-Drop error in Foundry V10 - issue: #41
#0.8
- Merged PR [League-of-Foundry-Developers/compendium-browser#40](https://github.com/League-of-Foundry-Developers/compendium-browser/pull/40): Foundry v10 support
#0.7
Works only with Foundry v0.8 and 9
##0.7.2
- Merged PR [League-of-Foundry-Developers/compendium-browser#33](https://github.com/League-of-Foundry-Developers/compendium-browser/pull/33)
- Fixed: Issue [League-of-Foundry-Developers/compendium-browser#29](https://github.com/League-of-Foundry-Developers/compendium-browser/issues/29)
- Fixed: Issue [League-of-Foundry-Developers/compendium-browser#30](https://github.com/League-of-Foundry-Developers/compendium-browser/issues/30)
- Fixed: Issue [League-of-Foundry-Developers/compendium-browser#31](https://github.com/League-of-Foundry-Developers/compendium-browser/issues/31)
- Change message to "Loading..." until we're done, then "Loaded" (also when we hit the maxLoaded)
##0.7.1
- Merged PR [League-of-Foundry-Developers/compendium-browser#26](https://github.com/League-of-Foundry-Developers/compendium-browser/pull/26)
- Fixed: Issue [League-of-Foundry-Developers/compendium-browser#25](https://github.com/League-of-Foundry-Developers/compendium-browser/issues/25)
##v0.7.0 (only Foundry 0.8+)
- Merged PR #24 (performance speed ups)
- Fixed: Issue [League-of-Foundry-Developers/compendium-browser#19](https://github.com/League-of-Foundry-Developers/compendium-browser/issues/19)
- Fixed: Issue [League-of-Foundry-Developers/compendium-browser#7](https://github.com/League-of-Foundry-Developers/compendium-browser/issues/7)
##v0.6.0
- Merged PR #14, #8 (classes for new spells and Optional Class Features in Tasha's)
- Manually merged PR #3 (German and Spanish translations)
##v0.5.0
- Fixed: Issue #17 (error in filtering NPCs by Creature Type)
##v0.4.5
- Fixed: [Suggestion] Show compendium source in results; Issue #11
- Fixed: Spells from non-system compendium show up in items tab. Issue#10
##v0.4.3
##v0.3.1
- fixed a bug that prevented loading when Class type items were loaded.
- fixed a bug that prevented disabled the scrollbar in the settings tab.
##v0.3.0
- improved load times by lazyloading images
- fixed some css problems
- new Feature: Feat Browser
- Compendium Browser now has a new section for Feats
- lets you filter by source, class (as set in the requirements field), activation cost, damage type and if it uses ressources
- new Feature: Item Browser
- Compendium Browser now has a new section for all inventory Items
- All item Packs (such as Explorer's Pack) are configured and you can browse a List of all Items contained in a pack!
- this list can be modified by editing the "item-packs.json" file to customize your packs
- many further filters available!
##v0.2.1
- fixed an issue that prevented the rendering of the Button to open the browser
##v0.2
- fixed a bug that could prevent proper npc loading
- added a filter for "Source" for both spells and npcs
- migrated to the new TabsV2
- added a Reset Filters button
- Added the Artificer class, thanks to Tielc#7191 for that

65
CONTRIBUTING.md 100644
View File

@ -0,0 +1,65 @@
## Development
### Prerequisites
In order to build this module, recent versions of `node` and `npm` are
required. Most likely, using `yarn` also works, but only `npm` is officially
supported. We recommend using the latest lts version of `node`. If you use `nvm`
to manage your `node` versions, you can simply run
```
nvm install
```
in the project's root directory.
You also need to install the project's dependencies. To do so, run
```
npm install
```
### Building
You can build the project by running
```
npm run build
```
Alternatively, you can run
```
npm run build:watch
```
to watch for changes and automatically build as necessary.
### Linking the built project to Foundry VTT
In order to provide a fluent development experience, it is recommended to link
the built module to your local Foundry VTT installation's data folder. In
order to do so, first add a file called `foundryconfig.json` to the project root
with the following content:
```
{
"dataPath": ["/absolute/path/to/your/FoundryVTT"]
}
```
(if you are using Windows, make sure to use `\` as a path separator instead of
`/`)
Then run
```
npm run link-project
```
On Windows, creating symlinks requires administrator privileges, so
unfortunately you need to run the above command in an administrator terminal for
it to work.
You can also link to multiple data folders by specifying multiple paths in the
`dataPath` array.

View File

@ -1,6 +0,0 @@
v0.2
- fixed a bug that could prevent proper npc loading
- added a filter for "Source" for both spells and npcs
- migrated to the new TabsV2
- added a Reset Filters button
- Added the Artificer class, thanks to Tielc#7191 for that

View File

@ -1,29 +1,20 @@
# Compendium Browser
> This version only works for Foundry v0.4.4 and up. To use the previous version please visit https://github.com/syl3r86/compendium-browser/tree/pre-0.4.4
A module to easily browse and filter spells as well as npcs loaded from compendie.
## Installation
1. Copy this link and use it in Foundrys Module Manager to install the Module
> https://raw.githubusercontent.com/syl3r86/compendium-browser/master/module.json
2. Enable the Module in your Worlds Module Settings
Tired of scrolling compendia? Easily browse and filter for spells, feats, items, and actors using Compendium Browser.
![example](preview.jpg)
## Details
Only the Gamemaster has access to the Settings, where they can enable or disable player access to the spell or npc-browser. It is **highly** recommended to disable any compendie that do not contain spell or should not be used in the NPC Browser. This reduces the initial loading time, that happens after a client connects to foundry, immensly.
This application enables anyone to add their own custom spell or npc filters via the api. After initialization the app can be found under game.compendiumBrowser where either addSpellFilter or addNpcFilter can be used to add a filter. This does support any data that the spell or npc has, including flags.
Only the Gamemaster has access to the Settings, where they can enable or disable player access to specific tabs.
All filters featured in the app are included in this manor and can be found in the compendium-browser.js at around line 726.
## Contribution
If you feel like supporting my work, feel free to leave a tip at my paypal felix.mueller.86@web.de
### Adding your own filters
You can add your own filter to by calling `game.compendiumBrowser.addSpellFilter`, `game.compendiumBrowser.addNpcFilter`, `game.compendiumBrowser.addFeatFilter`, and `game.compendiumBrowser.addItemFilter`. This does support any data that the spell or npc has, including flags.
## License
<a rel="license" href="http://creativecommons.org/licenses/by/4.0/"><img alt="Creative Commons Licence" style="border-width:0" src="https://i.creativecommons.org/l/by/4.0/88x31.png" /></a><br /><span xmlns:dct="http://purl.org/dc/terms/" property="dct:title">Compendium Browser - a module for Foundry VTT -</span> by <a xmlns:cc="http://creativecommons.org/ns#" href="https://github.com/syl3r86?tab=repositories" property="cc:attributionName" rel="cc:attributionURL">Felix Müller</a> is licensed under a <a rel="license" href="http://creativecommons.org/licenses/by/4.0/">Creative Commons Attribution 4.0 International License</a>.
This work is licensed under Foundry Virtual Tabletop [EULA - Limited License Agreement for module development v 0.1.6](http://foundryvtt.com/pages/license.html).
This project is a fork of Compendium Browser by [Felix Müller](https://github.com/syl3r86).
## Community Contribution
See the [CONTRIBUTING](/CONTRIBUTING.md) file for information about how you can help this project.

View File

@ -1,219 +0,0 @@
/* core foundry changes
#compendium.flexcolumn.active {
display: flex;
flex-direction: column;
}
#compendium.flexcolumn > .directory-list {
width: 100%;
height: auto;
flex-basis: 0;
flex-grow: 1;
}
#compendium.flexcolumn > .directory-footer {
height: auto;
}
#compendium.flexcolumn > .directory-footer > * {
margin-top: 5px;
}
*/
#compendium .directory-footer .compendium-browser-btn {
margin-top: 5px;
}
#compendium .directory-footer {
display: block;
}
/* spellbrowser */
/* resizing */
.compendium-browser {
max-width: 1100px;
max-height: 90vh;
}
.compendium-browser .tabs {
max-height: 2em;
border-bottom: solid #782e22;
}
.compendium-browser .tabContainer {
height: calc(100% - 2em);
}
.compendium-browser .tabContainer .tab {
width: 100%;
height: 100%;
overflow: scroll;
}
.compendium-browser .control-area {
position: sticky;
display: block;
min-width: 250px;
max-width: 400px;
width: 300px;
height: 100%;
padding-right: 5px;
overflow: scroll;
}
.compendium-browser .control-area button {
background: rgba(0, 0, 0, 0.05);
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding: 2px;
}
.compendium-browser .control-area .filtercontainer {
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding: 2px;
}
.compendium-browser .control-area .filtercontainer h3 {
margin: 0;
cursor: pointer;
}
.compendium-browser .control-area .filtercontainer dl,
.compendium-browser .control-area .filtercontainer div {
margin: 5px 0;
}
.compendium-browser .control-area .filtercontainer dt {
display: inline-block;
width: 40%;
padding-left: 5px;
}
.compendium-browser .control-area .filtercontainer dd {
display: inline-block;
width: 58%;
margin-left: 0;
}
.compendium-browser .control-area .filtercontainer dd select {
width: 100%;
}
.compendium-browser .control-area .filtercontainer .multiselect {
border: 1px solid #bbb;
border-radius: 3px;
vertical-align: middle;
line-height: 32px;
margin: 2px 0;
}
.compendium-browser .control-area .filtercontainer .multiselect label {
padding: 5px;
}
.compendium-browser .control-area .filtercontainer .multiselect input {
vertical-align: middle;
}
.compendium-browser .control-area .filtercontainer .small-input {
width: calc(100% - 44px);
height: 27px;
background: rgba(0, 0, 0, 0.05);
border: 1px solid #444;
border-radius: 3px;
padding: 0 3px;
text-overflow: ellipsis;
}
.compendium-browser .control-area .filtercontainer .small-select {
width: 40px;
}
.compendium-browser .browser .window-content {
overflow-y: hidden!important;
}
.compendium-browser .browser ul {
float: right;
display: block;
min-width: 335px;
width: 785px;
margin: 0;
height: 100%;
overflow: auto;
padding-left: 5px;
}
.compendium-browser .browser ul .filter-tags {
display: none;
}
.compendium-browser .browser ul li span {
white-space: nowrap;
overflow: hidden;
}
.compendium-browser .browser .spacer {
display: inline-block;
min-width: 5px;
}
.compendium-browser .browser .spacer-large {
display: inline-block;
min-width: 15px;
}
.compendium-browser .spell-browser .spell {
cursor: default;
vertical-align: middle;
line-height: 32px;
margin: 2px 0;
}
.compendium-browser .spell-browser .spell .spell-image {
max-width: 32px;
height: 32px;
}
.compendium-browser .spell-browser .spell .spell-name {
height: 32px;
padding-left: 5px;
}
.compendium-browser .spell-browser .spell .spell-level {
text-align: center;
font-weight: 900;
max-width: 18px;
height: 32px;
}
.compendium-browser .spell-browser .spell .spell-tags {
text-align: right;
margin-right: 3px;
font-weight: 900;
max-width: 100px;
height: 32px;
}
.compendium-browser .npc-browser .npc {
cursor: default;
vertical-align: middle;
line-height: 64px;
margin: 4px 0;
}
.compendium-browser .npc-browser .npc .npc-image {
max-width: 64px;
height: 64px;
}
.compendium-browser .npc-browser .npc .npc-image img {
width: 64px;
height: 64px;
border: none;
object-fit: contain;
}
.compendium-browser .npc-browser .npc .npc-line {
line-height: 25px;
padding: 9px 0 5px 5px;
}
.compendium-browser .npc-browser .npc .npc-name {
font-weight: bold;
font-size: 16px;
}
.compendium-browser .npc-browser .npc .cr {
display: inline-block;
width: 55px;
}
.compendium-browser .npc-browser .npc .size {
display: inline-block;
width: 75px;
}
.compendium-browser .npc-browser .npc .type {
display: inline-block;
}
.compendium-browser .settings .settings-group {
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding: 2px;
}
.compendium-browser .settings .settings-group h3 {
margin: 0;
cursor: pointer;
}
.compendium-browser .settings .settings-group label {
display: block;
}
.compendium-browser .settings .settings-group h4 {
display: inline-block;
vertical-align: middle;
height: 100%;
}

View File

@ -1,815 +0,0 @@
/**
* @author Felix Müller aka syl3r86
* @version 0.2.0
*/
class SpellBrowser extends Application {
async initializeContent() {
// load settings
if (this.settings === undefined) {
this.initSettings();
}
this.loadSpells().then(obj => {
this.spells = obj;
});
this.loadNpcs().then(obj => {
this.npcs = obj;
});
await loadTemplates([
"modules/compendium-browser/template/spell-browser.html",
"modules/compendium-browser/template/npc-browser.html",
"modules/compendium-browser/template/filter-container.html",
"modules/compendium-browser/template/settings.html"
]);
this.hookCompendiumList();
this.spellFilters = {
registeredFilterCategorys: {},
activeFilters: {}
};
this.npcFilters = {
registeredFilterCategorys: {},
activeFilters: {}
};
}
static get defaultOptions() {
const options = super.defaultOptions;
mergeObject(options, {
tabs: [{ navSelector: ".tabs", contentSelector: ".content", initial: "spell" }],
classes: options.classes.concat('compendium-browser'),
template: "modules/compendium-browser/template/template.html",
width: 800,
height: 700,
resizable: true,
minimizable: true,
title: "Compendium Browser"
});
return options;
}
hookCompendiumList() {
Hooks.on('renderCompendiumDirectory', (app, html, data) => {
if (this.settings === undefined) {
this.initSettings();
}
if (game.user.isGM || this.settings.allowSpellBrowser || this.settings.allowNpcBrowser) {
const importButton = $(`<button class="compendium-browser-btn"><i class="fas fa-fire"></i> ${game.i18n.localize("CMPBrowser.compendiumBrowser")}</button>`);
html.find('.compendium-browser-btn').remove();
// adding to directory-list since the footer doesn't exist if the user is not gm
html.find('.directory-footer').append(importButton);
// Handle button clicks
importButton.click(ev => {
ev.preventDefault();
this.render(true);
});
}
});
}
async getData() {
if (!this.spellsLoaded) {
// spells will be stored locally to not require full loading each time the browser is opened
this.spells = await this.loadSpells();
this.spellsLoaded = true;
}
let data = {};
data.spells = this.spells;
data.spellFilters = this.spellFilters;
data.showSpellBrowser = (game.user.isGM || this.settings.allowSpellBrowser);
data.npcs = this.npcs;
data.npcFilters = this.npcFilters;
data.showNpcBrowser = (game.user.isGM || this.settings.allowNpcBrowser);
data.settings = this.settings;
data.isGM = game.user.isGM;
return data;
}
async loadSpells() {
console.log('Spell Browser | Started loading spells');
if (this.classList === undefined) {
this.classList = await fetch('modules/compendium-browser/spell-classes.json').then(result => {
return result.json();
}).then(obj => {
return this.classList = obj;
});
}
this.spellsLoaded = false;
this.spellsLoading = true;
let unfoundSpells = '';
let spells = {};
for (let pack of game.packs) {
if (pack['metadata']['entity'] == "Item" && this.settings.loadedSpellCompendium[pack.collection].load) {
await pack.getContent().then(content => {
for (let spell of content) {
spell = spell.data;
if (spell.type == 'spell') {
spell.compendium = pack.collection;
// determining classes that can use the spell
let cleanSpellName = spell.name.toLowerCase().replace(/[^一-龠ぁ-ゔァ-ヴーa-zA-Z0-9---9々〆〤]/g, '').replace("'", '').replace(/ /g, '');
//let cleanSpellName = spell.name.toLowerCase().replace(/[^a-zA-Z0-9\s:]/g, '').replace("'", '').replace(/ /g, '');
if (this.classList[cleanSpellName] !== undefined) {
let classes = this.classList[cleanSpellName];
spell.data.classes = classes.split(',');
} else {
unfoundSpells += cleanSpellName + ',';
}
// getting damage types
spell.damageTypes = [];
if (spell.data.damage && spell.data.damage.parts.length > 0) {
for (let part of spell.data.damage.parts) {
let type = part[1];
if (spell.damageTypes.indexOf(type) === -1) {
spell.damageTypes.push(type);
}
}
}
spells[(spell._id)] = spell;
}
}
});
}
}
if (unfoundSpells !== '') {
console.log(`Spell Browser | List of Spells that don't have a class assosiated to them:`);
console.log(unfoundSpells);
}
console.log('Spell Browser | Finished loading spells');
return spells;
}
async loadNpcs() {
console.log('NPC Browser | Started loading spells');
let npcs = {};
for (let pack of game.packs) {
if (pack['metadata']['entity'] == "Actor" && this.settings.loadedNpcCompendium[pack.collection].load) {
await pack.getContent().then(async content => {
for (let npc of content) {
npc = npc.data;
// add needed data
npc.compendium = pack.collection;
// cr display
let cr = npc.data.details.cr;
if (cr == undefined || cr == '') cr = 0;
else cr = Number(cr);
if (cr > 0 && cr < 1) cr = "1/" + (1 / cr);
npc.displayCR = cr;
npc.displaySize = 'unset';
npc.filterSize = 2;
if (CONFIG.DND5E.actorSizes[npc.data.traits.size] !== undefined) {
npc.displaySize = CONFIG.DND5E.actorSizes[npc.data.traits.size];
}
switch (npc.data.traits.size) {
case 'grg': npc.filterSize = 5; break;
case 'huge': npc.filterSize = 4; break;
case 'lg': npc.filterSize = 3; break;
case 'sm': npc.filterSize = 1; break;
case 'tiny': npc.filterSize = 0; break;
case 'med':
default: npc.filterSize = 2; break;
}
// getting value for HasSpells and damage types
npc.hasSpells = false;
npc.damageDealt = [];
for (let item of npc.items) {
if (item.type == 'spell') {
npc.hasSpells = true;
}
if (item.data.damage && item.data.damage.parts && item.data.damage.parts.length > 0) {
for (let part of item.data.damage.parts) {
let type = part[1];
if (npc.damageDealt.indexOf(type) === -1) {
npc.damageDealt.push(type);
}
}
}
}
npcs[npc._id] = npc;
}
});
}
}
console.log('NPC Browser | Finished loading NPCs');
return npcs;
}
activateListeners(html) {
super.activateListeners(html);
// localizing title
$(html).parents('.app').find('.window-title')[0].innerText = game.i18n.localize("CMPBrowser.compendiumBrowser");
// show entity sheet
html.find('.item-edit').click(ev => {
let itemId = $(ev.currentTarget).parents("li").attr("data-entry-id");
let compendium = $(ev.currentTarget).parents("li").attr("data-entry-compendium");
let pack = game.packs.find(p => p.collection === compendium);
pack.getEntity(itemId).then(entity => {
entity.sheet.render(true);
});
});
// make draggable
html.find('.draggable').each((i, li) => {
li.setAttribute("draggable", true);
li.addEventListener('dragstart', event => {
let packName = li.getAttribute("data-entry-compendium");
let pack = game.packs.find(p => p.collection === packName);
if (!pack) {
event.preventDefault();
return false;
}
event.dataTransfer.setData("text/plain", JSON.stringify({
type: pack.entity,
pack: pack.collection,
id: li.getAttribute("data-entry-id")
}));
}, false);
});
// toggle visibility of filter containers
html.find('.filtercontainer h3, .multiselect label').click(async ev => {
await $(ev.target.nextElementSibling).toggle(100);
});
html.find('.multiselect label').trigger('click');
// sort spell list
html.find('.spell-browser select[name=sortorder]').on('change', ev => {
let spellList = html.find('.spell-browser li');
let byName = (ev.target.value == 'true');
let sortedList = this.sortSpells(spellList, byName);
let ol = $(html.find('.spell-browser ul'));
ol[0].innerHTML = [];
for (let element of sortedList) {
ol[0].append(element);
}
});
html.find('.spell-browser select[name=sortorder]').trigger('change');
// sort npc list
html.find('.npc-browser select[name=sortorder]').on('change', ev => {
let npcList = html.find('.npc-browser li');
let orderBy = ev.target.value;
let sortedList = this.sortNpcs(npcList, orderBy);
let ol = $(html.find('.npc-browser ul'));
ol[0].innerHTML = [];
for (let element of sortedList) {
ol[0].append(element);
}
});
html.find('.npc-browser select[name=sortorder]').trigger('change')
// reset filters
html.find('#reset-spell-filter').click(ev => {
this.spellFilters.activeFilters = {};
this.render();
});
html.find('#reset-npc-filter').click(ev => {
this.npcFilters.activeFilters = {};
this.render();
});
// settings
html.find('.settings input').on('change', ev => {
let setting = ev.target.dataset.setting;
let value = ev.target.checked;
if (setting === 'spell-compendium-setting') {
let key = ev.target.dataset.key;
this.settings.loadedSpellCompendium[key].load = value;
this.loadSpells().then((spells) => {
this.spells = spells;
this.render();
});
ui.notifications.info("Settings Saved. Spell Compendiums are being reloaded.");
} else if (setting === 'npc-compendium-setting') {
let key = ev.target.dataset.key;
this.settings.loadedNpcCompendium[key].load = value;
this.loadNpcs().then((npcs) => {
this.npcs = npcs;
this.render();
});
ui.notifications.info("Settings Saved. NPC Compendiums are being reloaded.");
}
if (setting === 'allow-spell-browser') {
this.settings.allowSpellBrowser = value;
}
if (setting === 'allow-npc-browser') {
this.settings.allowNpcBrowser = value;
}
this.saveSettings();
});
// activating or deactivating filters
// text filters
html.find('.filter[data-type=text] input, .filter[data-type=text] select').on('keyup change paste', ev => {
let path = $(ev.target).parents('.filter').data('path');
let key = path.replace(/\./g, '');
let value = ev.target.value;
let itemType = $(ev.target).parents('.tab').data('tab');
let filterTarget = `${itemType}Filters`;
if (value === '' || value === undefined) {
delete this[filterTarget].activeFilters[key];
} else {
this[filterTarget].activeFilters[key] = {
path: path,
type: 'text',
valIsArray: false,
value: ev.target.value
}
}
let list = null;
let subjects = null;
if (itemType === 'spell') {
list = html.find('.spell-browser li');
subjects = this.spells;
} else if (itemType === 'npc') {
list = html.find('.npc-browser li');
subjects = this.npcs;
}
this.filterElements(list, subjects, this[filterTarget].activeFilters);
});
// select filters
html.find('.filter[data-type=select] select, .filter[data-type=bool] select').on('change', ev => {
let path = $(ev.target).parents('.filter').data('path');
let key = path.replace(/\./g, '');
let filterType = $(ev.target).parents('.filter').data('type');
let itemType = $(ev.target).parents('.tab').data('tab');
let valIsArray = $(ev.target).parents('.filter').data('valisarray');
if (valIsArray === 'true') valIsArray = true;
let value = ev.target.value;
if (value === 'false') value = false;
if (value === 'true') value = true;
let filterTarget = `${itemType}Filters`;
if (value === "null") {
delete this[filterTarget].activeFilters[key]
} else {
this[filterTarget].activeFilters[key] = {
path: path,
type: filterType,
valIsArray: valIsArray,
value:value
}
}
let list = null;
let subjects = null;
if (itemType === 'spell') {
list = html.find('.spell-browser li');
subjects = this.spells;
} else if (itemType === 'npc') {
list = html.find('.npc-browser li');
subjects = this.npcs;
}
this.filterElements(list, subjects, this[filterTarget].activeFilters);
});
// multiselect filters
html.find('.filter[data-type=multiSelect] input').on('change', ev => {
let path = $(ev.target).parents('.filter').data('path');
let key = path.replace(/\./g, '');
let filterType = 'multiSelect';
let itemType = $(ev.target).parents('.tab').data('tab');
let valIsArray = $(ev.target).parents('.filter').data('valisarray');
if (valIsArray === 'true') valIsArray = true;
let value = $(ev.target).data('value');
let filterTarget = `${itemType}Filters`;
let filter = this[filterTarget].activeFilters[key];
if (ev.target.checked === true) {
if (filter === undefined) {
this[filterTarget].activeFilters[key] = {
path: path,
type: filterType,
valIsArray: valIsArray,
values: [ value ]
}
} else {
this[filterTarget].activeFilters[key].values.push(value);
}
} else {
delete this[filterTarget].activeFilters[key].values.splice(this[filterTarget].activeFilters[key].values.indexOf(value),1);
if (this[filterTarget].activeFilters[key].values.length === 0) {
delete this[filterTarget].activeFilters[key];
}
}
let list = null;
let subjects = null;
if (itemType === 'spell') {
list = html.find('.spell-browser li');
subjects = this.spells;
} else if (itemType === 'npc') {
list = html.find('.npc-browser li');
subjects = this.npcs;
}
this.filterElements(list, subjects, this[filterTarget].activeFilters);
});
html.find('.filter[data-type=numberCompare] select, .filter[data-type=numberCompare] input').on('change keyup paste', ev => {
let path = $(ev.target).parents('.filter').data('path');
let key = path.replace(/\./g, '');
let filterType = 'numberCompare';
let itemType = $(ev.target).parents('.tab').data('tab');
let valIsArray = false;
let operator = $(ev.target).parents('.filter').find('select').val();
let value = $(ev.target).parents('.filter').find('input').val();
let filterTarget = `${itemType}Filters`;
if (value === '' || operator === 'null') {
delete this[filterTarget].activeFilters[key]
} else {
this[filterTarget].activeFilters[key] = {
path: path,
type: filterType,
valIsArray: valIsArray,
operator: operator,
value: value
}
}
let list = null;
let subjects = null;
if (itemType === 'spell') {
list = html.find('.spell-browser li');
subjects = this.spells;
} else if (itemType === 'npc') {
list = html.find('.npc-browser li');
subjects = this.npcs;
}
this.filterElements(list, subjects, this[filterTarget].activeFilters);
});
}
sortSpells(list, byName) {
if(byName) {
list.sort((a, b) => {
let aName = $(a).find('.spell-name a')[0].innerHTML;
let bName = $(b).find('.spell-name a')[0].innerHTML;
if (aName < bName) return -1;
if (aName > bName) return 1;
return 0;
});
} else {
list.sort((a, b) => {
let aVal = $(a).find('input[name=level]').val();
let bVal = $(b).find('input[name=level]').val();
if (aVal < bVal) return -1;
if (aVal > bVal) return 1;
if (aVal == bVal) {
let aName = $(a).find('.spell-name a')[0].innerHTML;
let bName = $(b).find('.spell-name a')[0].innerHTML;
if (aName < bName) return -1;
if (aName > bName) return 1;
return 0;
}
});
}
return list;
}
sortNpcs(list, orderBy) {
switch (orderBy) {
case 'name':
list.sort((a, b) => {
let aName = $(a).find('.npc-name a')[0].innerHTML;
let bName = $(b).find('.npc-name a')[0].innerHTML;
if (aName < bName) return -1;
if (aName > bName) return 1;
return 0;
}); break;
case 'cr':
list.sort((a, b) => {
let aVal = Number($(a).find('input[name="order.cr"]').val());
let bVal = Number($(b).find('input[name="order.cr"]').val());
if (aVal < bVal) return -1;
if (aVal > bVal) return 1;
if (aVal == bVal) {
let aName = $(a).find('.npc-name a')[0].innerHTML;
let bName = $(b).find('.npc-name a')[0].innerHTML;
if (aName < bName) return -1;
if (aName > bName) return 1;
return 0;
}
}); break;
case 'size':
list.sort((a, b) => {
let aVal = $(a).find('input[name="order.size"]').val();
let bVal = $(b).find('input[name="order.size"]').val();
if (aVal < bVal) return -1;
if (aVal > bVal) return 1;
if (aVal == bVal) {
let aName = $(a).find('.npc-name a')[0].innerHTML;
let bName = $(b).find('.npc-name a')[0].innerHTML;
if (aName < bName) return -1;
if (aName > bName) return 1;
return 0;
}
}); break;
}
return list;
}
filterElements(list, subjects, filters) {
for (let element of list) {
let subject = subjects[element.dataset.entryId];
if (this.getFilterResult(subject, filters) == false) {
$(element).hide();
} else {
$(element).show();
}
}
}
getFilterResult(subject, filters) {
for (let filterKey in filters) {
let filter = filters[filterKey];
let prop = getProperty(subject, filter.path);
if (filter.type === 'numberCompare') {
switch (filter.operator) {
case '=': if (prop != filter.value) { return false; } break;
case '<': if (prop >= filter.value) { return false; } break;
case '>': if (prop <= filter.value) { return false; } break;
}
continue;
}
if (filter.valIsArray === false) {
if (filter.type === 'text') {
if (prop.toLowerCase().indexOf(filter.value.toLowerCase()) === -1) {
return false;
}
} else {
if (filter.value !== undefined && prop !== undefined && prop != filter.value && !(filter.value === true && prop)) {
return false;
}
if (filter.values && filter.values.indexOf(prop) === -1) {
return false;
}
}
} else {
if (prop === undefined) return false;
if (typeof prop === 'object') {
if (filter.value) {
if (prop.indexOf(filter.value) === -1) {
return false;
}
} else if(filter.values) {
for (let val of filter.values) {
if (prop.indexOf(val) !== -1) {
continue;
}
return false;
}
}
} else {
console.log(prop);
for (let val of filter.values) {
if (prop === val) {
continue;
}
}
return false;
}
}
}
return true;
}
clearObject(obj) {
let newObj = {};
for (let key in obj) {
if (obj[key] == true) {
newObj[key] = true;
}
}
return newObj;
}
initSettings() {
let defaultSettings = {
loadedSpellCompendium: {},
loadedNpcCompendium: {},
};
for (let compendium of game.packs) {
if (compendium['metadata']['entity'] == "Item") {
defaultSettings.loadedSpellCompendium[compendium.collection] = {
load: true,
name: `${compendium['metadata']['label']} (${compendium.collection})`
};
}
if (compendium['metadata']['entity'] == "Actor") {
defaultSettings.loadedNpcCompendium[compendium.collection] = {
load: true,
name: `${compendium['metadata']['label']} (${compendium.collection})`
};
}
}
// creating game setting container
game.settings.register("compendiumBrowser", "settings", {
name: "Compendium Browser Settings",
hint: "Settings to exclude packs from loading and visibility of the browser",
default: defaultSettings,
type: Object,
scope: 'world',
onChange: settings => {
this.settings = settings;
}
});
// load settings from container and apply to default settings (available compendie might have changed)
let settings = game.settings.get('compendiumBrowser', 'settings');
for (let compKey in defaultSettings.loadedSpellCompendium) {
if (settings.loadedSpellCompendium[compKey] !== undefined) {
defaultSettings.loadedSpellCompendium[compKey].load = settings.loadedSpellCompendium[compKey].load;
}
}
for (let compKey in defaultSettings.loadedNpcCompendium) {
if (settings.loadedNpcCompendium[compKey] !== undefined) {
defaultSettings.loadedNpcCompendium[compKey].load = settings.loadedNpcCompendium[compKey].load;
}
}
defaultSettings.allowSpellBrowser = settings.allowSpellBrowser;
defaultSettings.allowNpcBrowser = settings.allowNpcBrowser;
if (game.user.isGM) {
game.settings.set('compendiumBrowser', 'settings', defaultSettings);
}
this.settings = defaultSettings;
}
saveSettings() {
game.settings.set('compendiumBrowser', 'settings', this.settings);
}
addFilter(entityType, category, label, path, type, possibleValues = null, valIsArray = false) {
let target = `${entityType}Filters`;
let filter = {};
filter.path = path;
filter.label = label;
filter.type = 'text';
if (['text', 'bool', 'select', 'multiSelect', 'numberCompare'].indexOf(type) !== -1) {
filter[`is${type}`] = true;
filter.type = type;
}
if (possibleValues !== null) {
filter.possibleValues = possibleValues;
}
filter.valIsArray = valIsArray;
let catId = category.replace(/\W/g, '');
if (this[target].registeredFilterCategorys[catId] === undefined) {
this[target].registeredFilterCategorys[catId] = { label: category, filters: [] };
}
this[target].registeredFilterCategorys[catId].filters.push(filter);
}
/**
* Used to add custom filters to the Spell-Browser
* @param {String} category - Title of the category
* @param {String} label - Title of the filter
* @param {String} path - path to the data that the filter uses. uses dotnotation. example: data.abilities.dex.value
* @param {String} type - type of filter
* possible filter:
* text: will give a textinput (or use a select if possibleValues has values) to compare with the data. will use objectData.indexOf(searchedText) to enable partial matching
* bool: will see if the data at the path exists and not false.
* select: exactly matches the data with the chosen selector from possibleValues
* multiSelect: enables selecting multiple values from possibleValues, any of witch has to match the objects data
* numberCompare: gives the option to compare numerical values, either with =, < or the > operator
* @param {Boolean} possibleValues - predetermined values to choose from. needed for select and multiSelect, can be used in text filters
* @param {Boolean} valIsArray - if the objects data is an object use this. the filter will check each property in the object (not recursive). if no match is found, the object will be hidden
*/
addSpellFilter(category, label, path, type, possibleValues = null, valIsArray = false) {
this.addFilter('spell', category, label, path, type, possibleValues, valIsArray);
}
/**
* Used to add custom filters to the Spell-Browser
* @param {String} category - Title of the category
* @param {String} label - Title of the filter
* @param {String} path - path to the data that the filter uses. uses dotnotation. example: data.abilities.dex.value
* @param {String} type - type of filter
* possible filter:
* text: will give a textinput (or use a select if possibleValues has values) to compare with the data. will use objectData.indexOf(searchedText) to enable partial matching
* bool: will see if the data at the path exists and not false.
* select: exactly matches the data with the chosen selector from possibleValues
* multiSelect: enables selecting multiple values from possibleValues, any of witch has to match the objects data
* numberCompare: gives the option to compare numerical values, either with =, < or the > operator
* @param {Boolean} possibleValues - predetermined values to choose from. needed for select and multiSelect, can be used in text filters
* @param {Boolean} valIsArray - if the objects data is an object use this. the filter will check each property in the object (not recursive). if no match is found, the object will be hidden
*/
addNpcFilter(category, label, path, type, possibleValues = null, valIsArray = false) {
this.addFilter('npc', category, label, path, type, possibleValues, valIsArray);
}
}
Hooks.on('ready', async function() {
if (game.compendiumBrowser === undefined) {
game.compendiumBrowser = new SpellBrowser();
await game.compendiumBrowser.initializeContent();
}
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("DND5E.Source"), 'data.source', 'text');
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.lvl"), 'data.level', 'multiSelect', [game.i18n.localize("CMPBrowser.cantip"), 1, 2, 3, 4, 5, 6, 7, 8, 9]);
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.school"), 'data.school', 'select', CONFIG.DND5E.spellSchools);
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.castingTime"), 'data.activation.type', 'select',
{
action: game.i18n.localize("DND5E.Action"),
bonus: game.i18n.localize("CMPBrowser.bonusAction"),
reaction: game.i18n.localize("CMPBrowser.reaction"),
minute: game.i18n.localize("DND5E.TimeMinute"),
hour: game.i18n.localize("DND5E.TimeHour"),
day: game.i18n.localize("DND5E.TimeDay")
});
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.spellType"), 'data.actionType', 'select', CONFIG.DND5E.itemActionTypes);
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.damageType"), 'damageTypes', 'select', CONFIG.DND5E.damageTypes);
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.class"), 'data.classes', 'select',
{
artificer: game.i18n.localize("CMPBrowser.artificer"),
bard: game.i18n.localize("CMPBrowser.bard"),
cleric: game.i18n.localize("CMPBrowser.cleric"),
druid: game.i18n.localize("CMPBrowser.druid"),
paladin: game.i18n.localize("CMPBrowser.paladin"),
ranger: game.i18n.localize("CMPBrowser.ranger"),
sorcerer: game.i18n.localize("CMPBrowser.sorcerer"),
warlock: game.i18n.localize("CMPBrowser.warlock"),
wizard: game.i18n.localize("CMPBrowser.wizard"),
}, true);
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.components"), game.i18n.localize("CMPBrowser.ritual"), 'data.components.ritual', 'bool');
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.components"), game.i18n.localize("CMPBrowser.concentration"), 'data.components.concentration', 'bool');
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.components"), game.i18n.localize("CMPBrowser.verbal"), 'data.components.vocal', 'bool');
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.components"), game.i18n.localize("CMPBrowser.somatic"), 'data.components.somatic', 'bool');
game.compendiumBrowser.addSpellFilter(game.i18n.localize("CMPBrowser.components"), game.i18n.localize("CMPBrowser.material"), 'data.components.material', 'bool');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("DND5E.Source"), 'data.details.source', 'text');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.size"), 'data.traits.size', 'select', CONFIG.DND5E.actorSizes);
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.hasSpells"), 'hasSpells', 'bool');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.hasLegAct"), 'data.resources.legact.max', 'bool');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.hasLegRes"), 'data.resources.legres.max', 'bool');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.cr"), 'data.details.cr', 'numberCompare');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.general"), game.i18n.localize("CMPBrowser.creatureType"), 'data.details.type', 'text', {
aberration: game.i18n.localize("CMPBrowser.aberration"),
beast: game.i18n.localize("CMPBrowser.beast"),
celestial: game.i18n.localize("CMPBrowser.celestial"),
construct: game.i18n.localize("CMPBrowser.construct"),
dragon: game.i18n.localize("CMPBrowser.dragon"),
elemental: game.i18n.localize("CMPBrowser.elemental"),
fey: game.i18n.localize("CMPBrowser.fey"),
fiend: game.i18n.localize("CMPBrowser.fiend"),
giant: game.i18n.localize("CMPBrowser.giant"),
humanoid: game.i18n.localize("CMPBrowser.humanoid"),
monstrosity: game.i18n.localize("CMPBrowser.monstrosity"),
ooze: game.i18n.localize("CMPBrowser.ooze"),
plant: game.i18n.localize("CMPBrowser.plant"),
undead: game.i18n.localize("CMPBrowser.undead")
});
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.abilities"), game.i18n.localize("DND5E.AbilityStr"), 'data.abilities.str.value', 'numberCompare');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.abilities"), game.i18n.localize("DND5E.AbilityDex"), 'data.abilities.dex.value', 'numberCompare');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.abilities"), game.i18n.localize("DND5E.AbilityCon"), 'data.abilities.con.value', 'numberCompare');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.abilities"), game.i18n.localize("DND5E.AbilityInt"), 'data.abilities.int.value', 'numberCompare');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.abilities"), game.i18n.localize("DND5E.AbilityWis"), 'data.abilities.wis.value', 'numberCompare');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.abilities"), game.i18n.localize("DND5E.AbilityCha"), 'data.abilities.cha.value', 'numberCompare');
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.dmgInteraction"), game.i18n.localize("DND5E.DamImm"), 'data.traits.di.value', 'multiSelect', CONFIG.DND5E.damageTypes, true);
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.dmgInteraction"), game.i18n.localize("DND5E.DamRes"), 'data.traits.dr.value', 'multiSelect', CONFIG.DND5E.damageTypes, true);
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.dmgInteraction"), game.i18n.localize("DND5E.DamVuln"), 'data.traits.dv.value', 'multiSelect', CONFIG.DND5E.damageTypes, true);
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.dmgInteraction"), game.i18n.localize("DND5E.ConImm"), 'data.traits.ci.value', 'multiSelect', CONFIG.DND5E.conditionTypes, true);
game.compendiumBrowser.addNpcFilter(game.i18n.localize("CMPBrowser.dmgInteraction"), game.i18n.localize("CMPBrowser.dmgDealt"), 'damageDealt', 'multiSelect', CONFIG.DND5E.damageTypes, true);
});

View File

@ -1,259 +0,0 @@
/* core foundry changes
#compendium.flexcolumn.active {
display: flex;
flex-direction: column;
}
#compendium.flexcolumn > .directory-list {
width: 100%;
height: auto;
flex-basis: 0;
flex-grow: 1;
}
#compendium.flexcolumn > .directory-footer {
height: auto;
}
#compendium.flexcolumn > .directory-footer > * {
margin-top: 5px;
}
*/
#compendium .directory-footer .compendium-browser-btn {
margin-top:5px;
}
#compendium .directory-footer {
display:block;
}
/* spellbrowser */
/* resizing */
.compendium-browser {
max-width:1100px;
max-height:90vh;
.tabs {
max-height:2em;
border-bottom: solid #782e22;
a {
}
}
.tabContainer {
height:calc(100% - 2em);
.tab {
width: 100%;
height: 100%;
overflow:scroll;
}
}
.control-area {
position:sticky;
display: block;
min-width: 250px;
max-width: 400px;
width: 300px;
height:100%;
padding-right:5px;
overflow:scroll;
button {
background: rgba(0, 0, 0, 0.05);
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding:2px;
}
.filtercontainer {
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding:2px;
h3 {
margin:0;
cursor:pointer;
}
dl, div {
margin: 5px 0;
}
dt {
display:inline-block;
width:40%;
padding-left:5px;
}
dd {
display:inline-block;
width:58%;
margin-left:0;
select {
width:100%;
}
}
.multiselect {
border: 1px solid #bbb;
border-radius: 3px;
vertical-align: middle;
line-height:32px;
margin:2px 0;
label {
padding:5px;
}
input {
vertical-align: middle;
}
}
.small-input {
width: calc(100% - 44px);
height: 27px;
background: rgba(0, 0, 0, 0.05);
border: 1px solid #444;
border-radius: 3px;
padding: 0 3px;
text-overflow: ellipsis;
}
.small-select {
width: 40px;
}
}
}
.browser {
.window-content {
overflow-y: hidden!important;
}
ul {
float:right;
display: block;
min-width: 335px;
width: 785px;
margin:0;
height: 100%;
overflow:auto;
padding-left: 5px;
.filter-tags {
display:none;
}
li {
span {
white-space: nowrap;
overflow:hidden;
}
}
}
.spacer {
display:inline-block;
min-width:5px;
}
.spacer-large {
display:inline-block;
min-width:15px;
}
}
.spell-browser {
.spell {
cursor:default;
vertical-align: middle;
line-height:32px;
margin:2px 0;
.spell-image {
max-width:32px;
height:32px;
}
.spell-name {
height:32px;
padding-left:5px;
}
.spell-level {
text-align:center;
font-weight:900;
max-width:18px;
height:32px;
}
.spell-tags {
text-align:right;
margin-right:3px;
font-weight:900;
max-width:100px;
height:32px;
}
}
}
.npc-browser {
.npc {
cursor:default;
vertical-align: middle;
line-height:64px;
margin:4px 0;
.npc-image {
max-width: 64px;
height: 64px;
}
.npc-image img {
width: 64px;
height: 64px;
border: none;
object-fit: contain;
}
.npc-line {
line-height: 25px;
padding: 9px 0 5px 5px;
}
.npc-name {
font-weight:bold;
font-size:16px;
}
.cr {
display: inline-block;
width: 55px;
}
.size {
display: inline-block;
width: 75px;
}
.type {
display: inline-block;
}
}
}
.settings {
.settings-group {
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding:2px;
h3 {
margin:0;
cursor:pointer;
}
label {
display:block;
}
input {
}
h4 {
display:inline-block;
vertical-align: middle;
height:100%;
}
}
}
}

176
gulpfile.mjs 100644
View File

@ -0,0 +1,176 @@
// SPDX-FileCopyrightText: 2022 Johannes Loher
// SPDX-FileCopyrightText: 2022 David Archibald
//
// SPDX-License-Identifier: MIT
import fs from "fs-extra";
import gulp from "gulp";
import less from "gulp-less";
import sourcemaps from "gulp-sourcemaps";
import path from "node:path";
import buffer from "vinyl-buffer";
import source from "vinyl-source-stream";
import yargs from "yargs";
import { hideBin } from "yargs/helpers";
import rollupStream from "@rollup/stream";
import rollupConfig from "./rollup.config.mjs";
/** ******************/
/* CONFIGURATION */
/** ******************/
const packageId = "compendium-browser";
const sourceDirectory = "./src";
const distDirectory = "./dist";
const stylesDirectory = `${sourceDirectory}/styles`;
const stylesExtension = "less";
const sourceFileExtension = "js";
const staticFiles = ["assets", "fonts", "lang", "packs", "templates", "module.json"];
/** ******************/
/* BUILD */
/** ******************/
let cache;
/**
* Build the distributable JavaScript code
*/
function buildCode() {
return rollupStream({ ...rollupConfig(), cache })
.on("bundle", (bundle) => {
cache = bundle;
})
.pipe(source(`${packageId}.js`))
.pipe(buffer())
.pipe(sourcemaps.init({ loadMaps: true }))
.pipe(sourcemaps.write("."))
.pipe(gulp.dest(`${distDirectory}/module`));
}
/**
* Build style sheets
*/
function buildStyles() {
return gulp
.src(`${stylesDirectory}/${packageId}.${stylesExtension}`)
.pipe(less())
.pipe(gulp.dest(`${distDirectory}/styles`));
}
/**
* Copy static files
*/
async function copyFiles() {
for (const file of staticFiles) {
if (fs.existsSync(`${sourceDirectory}/${file}`)) {
await fs.copy(`${sourceDirectory}/${file}`, `${distDirectory}/${file}`);
}
}
}
/**
* Watch for changes for each build step
*/
export function watch() {
gulp.watch(`${sourceDirectory}/**/*.${sourceFileExtension}`, { ignoreInitial: false }, buildCode);
gulp.watch(`${stylesDirectory}/**/*.${stylesExtension}`, { ignoreInitial: false }, buildStyles);
gulp.watch(
staticFiles.map((file) => `${sourceDirectory}/${file}`),
{ ignoreInitial: false },
copyFiles,
);
}
export const build = gulp.series(clean, gulp.parallel(buildCode, buildStyles, copyFiles));
/** ******************/
/* CLEAN */
/** ******************/
/**
* Remove built files from `dist` folder while ignoring source files
*/
export async function clean() {
const files = [...staticFiles, "module"];
if (fs.existsSync(`${stylesDirectory}/${packageId}.${stylesExtension}`)) {
files.push("styles");
}
console.log(" ", "Files to clean:");
console.log(" ", files.join("\n "));
for (const filePath of files) {
await fs.remove(`${distDirectory}/${filePath}`);
}
}
/** ******************/
/* LINK */
/** ******************/
/**
* Get the data paths of Foundry VTT based on what is configured in `foundryconfig.json`
*/
function getDataPaths() {
const config = fs.readJSONSync("foundryconfig.json");
const dataPath = config?.dataPath;
if (dataPath) {
const dataPaths = Array.isArray(dataPath) ? dataPath : [dataPath];
return dataPaths.map((dataPath) => {
if (typeof dataPath !== "string") {
throw new Error(
`Property dataPath in foundryconfig.json is expected to be a string or an array of strings, but found ${dataPath}`,
);
}
if (!fs.existsSync(path.resolve(dataPath))) {
throw new Error(`The dataPath ${dataPath} does not exist on the file system`);
}
return path.resolve(dataPath);
});
} else {
throw new Error("No dataPath defined in foundryconfig.json");
}
}
/**
* Link build to User Data folder
*/
export async function link() {
let destinationDirectory;
if (fs.existsSync(path.resolve(sourceDirectory, "module.json"))) {
destinationDirectory = "modules";
} else {
throw new Error("Could not find module.json");
}
const linkDirectories = getDataPaths().map((dataPath) =>
path.resolve(dataPath, "Data", destinationDirectory, packageId),
);
const argv = yargs(hideBin(process.argv)).option("clean", {
alias: "c",
type: "boolean",
default: false,
}).argv;
const clean = argv.c;
for (const linkDirectory of linkDirectories) {
if (clean) {
console.log(`Removing build in ${linkDirectory}.`);
await fs.remove(linkDirectory);
} else if (!fs.existsSync(linkDirectory)) {
console.log(`Linking dist to ${linkDirectory}.`);
await fs.ensureDir(path.resolve(linkDirectory, ".."));
await fs.symlink(path.resolve(distDirectory), linkDirectory);
} else {
console.log(`Skipped linking to ${linkDirectory}, as it already exists.`);
}
}
}

View File

@ -1,62 +0,0 @@
{
"CMPBrowser.compendiumBrowser":"Compendium Browser",
"CMPBrowser.sortBy":"Sort by",
"CMPBrowser.cr":"Challenge Rating",
"CMPBrowser.generalSettings":"General Settings",
"CMPBrowser.allowSpellAcc":"Allow Players Access to the spell browser",
"CMPBrowser.allowNpcAcc":"Allow Players Access to the npc browser",
"CMPBrowser.compSettingsSpell":"Spell Compendium Settings",
"CMPBrowser.compSettingsNpc":"NPC Compendium Settings",
"CMPBrowser.load":"Load",
"CMPBrowser.lvl":"Level",
"CMPBrowser.ritual":"Ritual",
"CMPBrowser.concentration":"Concentration",
"CMPBrowser.verbal":"Verbal",
"CMPBrowser.somatic":"Somatic",
"CMPBrowser.material":"Material",
"CMPBrowser.cantip":"Cantrip",
"CMPBrowser.school":"School",
"CMPBrowser.castingTime":"Casting Time",
"CMPBrowser.bonusAction":"Bonus Action",
"CMPBrowser.reaction":"Reaction",
"CMPBrowser.spellType":"Spell Type",
"CMPBrowser.damageType":"Damage Type",
"CMPBrowser.class":"Class",
"CMPBrowser.artificer":"Artificer",
"CMPBrowser.bard":"Bard",
"CMPBrowser.cleric":"Cleric",
"CMPBrowser.druid":"Druid",
"CMPBrowser.paladin":"Paladin",
"CMPBrowser.ranger":"Ranger",
"CMPBrowser.sorcerer":"Sorcerer",
"CMPBrowser.warlock":"Warlock",
"CMPBrowser.wizard":"Wizard",
"CMPBrowser.general":"General",
"CMPBrowser.components":"Components",
"CMPBrowser.hasSpells":"Has Spells",
"CMPBrowser.hasLegAct":"Has Legendary Actions",
"CMPBrowser.hasLegRes":"Has Legendary Resistance",
"CMPBrowser.creatureType":"Creature Type",
"CMPBrowser.aberration": "Aberration",
"CMPBrowser.beast": "Beast",
"CMPBrowser.celestial": "Celestial",
"CMPBrowser.construct": "construct",
"CMPBrowser.dragon": "Dragon",
"CMPBrowser.elemental": "Elemental",
"CMPBrowser.fey": "Fey",
"CMPBrowser.fiend": "Fiend",
"CMPBrowser.giant": "Giant",
"CMPBrowser.humanoid": "Humanoid",
"CMPBrowser.monstrosity": "Monstrosity",
"CMPBrowser.ooze": "Ooze",
"CMPBrowser.plant": "Plant",
"CMPBrowser.undead": "Undead",
"CMPBrowser.abilities": "Abilities",
"CMPBrowser.dmgInteraction": "Damage Interaction",
"CMPBrowser.dmgDealt": "Damage Dealt",
"CMPBrowser.size": "Size",
"CMPBrowser.spellBrowser":"Spell Browser",
"CMPBrowser.npcBrowser":"NPC Browser",
"CMPBrowser.settings":"Settings"
}

View File

@ -1,60 +0,0 @@
{
"CMPBrowser.compendiumBrowser":"Recherche dans les Compendium",
"CMPBrowser.sortBy":"Trié par",
"CMPBrowser.cr":"Niveau de la rencontre",
"CMPBrowser.generalSettings":"Paramètres généraux",
"CMPBrowser.allowSpellAcc":"Autoriser les joueurs à accéder aux listes de sorts",
"CMPBrowser.allowNpcAcc":"Autoriser les joueurs à accéder aux listes de PNJ",
"CMPBrowser.compSettingsSpell":"Paramètres de compendium de sorts",
"CMPBrowser.compSettingsNpc":"Paramètres de compendium de PNJ",
"CMPBrowser.load":"Charger",
"CMPBrowser.lvl":"Level",
"CMPBrowser.ritual":"Rituel",
"CMPBrowser.concentration":"Concentration",
"CMPBrowser.verbal":"Verbales",
"CMPBrowser.somatic":"Somatiques",
"CMPBrowser.material":"Matérielles",
"CMPBrowser.cantip":"Tours de magie",
"CMPBrowser.school":"Ecole",
"CMPBrowser.castingTime":"Durée d'incantation",
"CMPBrowser.bonusAction":"Action Bonus",
"CMPBrowser.reaction":"Réaction",
"CMPBrowser.spellType":"Type de sort",
"CMPBrowser.damageType":"Type de dégâts",
"CMPBrowser.class":"Classe",
"CMPBrowser.bard":"Barde",
"CMPBrowser.cleric":"Clerc",
"CMPBrowser.druid":"Druide",
"CMPBrowser.paladin":"Paladin",
"CMPBrowser.ranger":"Rôdeur",
"CMPBrowser.sorcerer":"Sorcier",
"CMPBrowser.warlock":"Ensorceleur",
"CMPBrowser.wizard":"Magicien",
"CMPBrowser.general":"Général",
"CMPBrowser.components":"Composants",
"CMPBrowser.hasSpells":"à des Sorts",
"CMPBrowser.hasLegAct":"à des Actions Légendaires",
"CMPBrowser.hasLegRes":"à des Resistances Légendaires",
"CMPBrowser.creatureType":"Type de Créature",
"CMPBrowser.aberration": "Aberration",
"CMPBrowser.beast": "Bête",
"CMPBrowser.celestial": "Céleste",
"CMPBrowser.construct": "Artificielles",
"CMPBrowser.dragon": "Dragon",
"CMPBrowser.elemental": "Elementaire",
"CMPBrowser.fey": "Fée",
"CMPBrowser.fiend": "Fiélon",
"CMPBrowser.giant": "Géant",
"CMPBrowser.humanoid": "Humanoïde",
"CMPBrowser.monstrosity": "Monstrueuse",
"CMPBrowser.ooze": "Vase",
"CMPBrowser.plant": "Plante",
"CMPBrowser.undead": "Morts-vivants",
"CMPBrowser.abilities": "Capacités",
"CMPBrowser.dmgInteraction": "Spécificité des dégâts",
"CMPBrowser.dmgDealt": "Type de dégats",
"CMPBrowser.size": "Taille",
"CMPBrowser.spellBrowser":"Recherche de sorts",
"CMPBrowser.npcBrowser":"Recherche de PNJ",
"CMPBrowser.settings":"Paramétrages"
}

View File

@ -1,60 +0,0 @@
{
"CMPBrowser.compendiumBrowser":"辞典ブラウザ",
"CMPBrowser.sortBy":"並び替え",
"CMPBrowser.cr":"難易度",
"CMPBrowser.generalSettings":"一般設定",
"CMPBrowser.allowSpellAcc":"プレイヤーに呪文辞典の使用を許可する。",
"CMPBrowser.allowNpcAcc":"プレイヤーにNPC辞典の使用を許可する。",
"CMPBrowser.compSettingsSpell":"呪文辞典設定",
"CMPBrowser.compSettingsNpc":"NPC辞典設定",
"CMPBrowser.load":"追加",
"CMPBrowser.lvl":"レベル",
"CMPBrowser.ritual":"儀式",
"CMPBrowser.concentration":"集中",
"CMPBrowser.verbal":"音声",
"CMPBrowser.somatic":"動作",
"CMPBrowser.material":"物質",
"CMPBrowser.cantip":"初級",
"CMPBrowser.school":"系統",
"CMPBrowser.castingTime":"発動時間",
"CMPBrowser.bonusAction":"ボーナスアクション",
"CMPBrowser.reaction":"リアクション",
"CMPBrowser.spellType":"呪文種別",
"CMPBrowser.damageType":"ダメージ種別",
"CMPBrowser.class":"クラス",
"CMPBrowser.bard":"バード",
"CMPBrowser.cleric":"クレリック",
"CMPBrowser.druid":"ドルイド",
"CMPBrowser.paladin":"パラディン",
"CMPBrowser.ranger":"レンジャー",
"CMPBrowser.sorcerer":"ソーサラー",
"CMPBrowser.warlock":"ウォーロック",
"CMPBrowser.wizard":"ウィザード",
"CMPBrowser.general":"一般",
"CMPBrowser.components":"物質構成要素",
"CMPBrowser.hasSpells":"術者",
"CMPBrowser.hasLegAct":"伝説的アクション所持",
"CMPBrowser.hasLegRes":"伝説的抵抗所持",
"CMPBrowser.creatureType":"クリーチャー種別",
"CMPBrowser.aberration": "異形",
"CMPBrowser.beast": "野獣",
"CMPBrowser.celestial": "セレスチャル",
"CMPBrowser.construct": "人造",
"CMPBrowser.dragon": "ドラゴン",
"CMPBrowser.elemental": "エレメンタル",
"CMPBrowser.fey": "フェイ",
"CMPBrowser.fiend": "フィーンド",
"CMPBrowser.giant": "巨人",
"CMPBrowser.humanoid": "ヒューマノイド",
"CMPBrowser.monstrosity": "怪物",
"CMPBrowser.ooze": "粘体",
"CMPBrowser.plant": "植物",
"CMPBrowser.undead": "アンデッド",
"CMPBrowser.abilities": "能力値",
"CMPBrowser.dmgInteraction": "ダメージ関連",
"CMPBrowser.dmgDealt": "与えるダメージ種別",
"CMPBrowser.size": "サイズ",
"CMPBrowser.spellBrowser":"呪文ブラウザ",
"CMPBrowser.npcBrowser":"NPCブラウザ",
"CMPBrowser.settings":"設定"
}

View File

@ -1,33 +0,0 @@
{
"name": "compendium-browser",
"title": "Compendium Browser",
"description": "A module to easily browse and filter spells as well as npcs loaded from compendie.",
"version": "0.2.0",
"author": "Felix#6196",
"systems": ["dnd5e"],
"scripts": ["./compendium-browser.js"],
"styles": ["./compendium-browser.css"],
"packs": [],
"languages": [
{
"lang": "en",
"name": "English",
"path": "lang/en.json"
},
{
"lang": "ja",
"name": "Japanese",
"path": "lang/ja.json"
},
{
"lang": "fr",
"name": "French (FRANCE)",
"path": "lang/fr.json"
}
],
"url": "https://github.com/syl3r86/compendium-browser",
"manifest": "https://raw.githubusercontent.com/syl3r86/compendium-browser/master/module.json",
"download": "https://github.com/syl3r86/compendium-browser/archive/v0.2.0.zip",
"minimumCoreVersion": "0.5.5",
"compatibleCoreVersion": "0.5.5"
}

11471
package-lock.json generated 100644

File diff suppressed because it is too large Load Diff

32
package.json 100644
View File

@ -0,0 +1,32 @@
{
"scripts": {
"build": "gulp build",
"build:watch": "gulp watch",
"link-project": "gulp link",
"clean": "gulp clean",
"clean:link": "gulp link --clean",
"lint": "eslint --ext .js,.cjs,.mjs .",
"lint:fix": "eslint --ext .js,.cjs,.mjs --fix .",
"postinstall": "husky install"
},
"devDependencies": {
"@rollup/plugin-node-resolve": "^15.2.3",
"@rollup/stream": "^3.0.1",
"@typhonjs-fvtt/eslint-config-foundry.js": "^0.8.0",
"eslint": "^8.53.0",
"fs-extra": "^11.1.1",
"gulp": "^4.0.2",
"gulp-less": "^5.0.0",
"gulp-sourcemaps": "^3.0.0",
"husky": "^8.0.3",
"less": "^3.13.1",
"lint-staged": "^15.0.2",
"rollup": "^2.79.1",
"vinyl-buffer": "^1.0.1",
"vinyl-source-stream": "^2.0.0",
"yargs": "^17.7.2"
},
"lint-staged": {
"*.(js|cjs|mjs)": "eslint --fix"
}
}

16
rollup.config.mjs 100644
View File

@ -0,0 +1,16 @@
// SPDX-FileCopyrightText: 2022 Johannes Loher
// SPDX-FileCopyrightText: 2022 David Archibald
//
// SPDX-License-Identifier: MIT
import { nodeResolve } from "@rollup/plugin-node-resolve";
export default () => ({
input: "src/module/compendium-browser.js",
output: {
dir: "dist/module",
format: "es",
sourcemap: true,
},
plugins: [nodeResolve()],
});

View File

@ -1,482 +0,0 @@
{
"abidalzimshorridwilting": "sorcerer,wizard",
"absorbelements": "artificer,druid,ranger,sorcerer,wizard",
"arcaneweapon": "artificerrevisited",
"acidsplash": "artificer,sorcerer,wizard,artificerrevisited",
"aganazzarsscorcher": "sorcerer,wizard",
"aid": "artificer,cleric,paladin,artificer,artificerrevisited",
"alarm": "artificer,ranger,wizard,artificer,artificerrevisited",
"alterself": "artificer,sorcerer,wizard,artificer,artificerrevisited",
"animalfriendship": "bard,druid,ranger",
"animalmessenger": "bard,druid,ranger",
"animalshapes": "druid",
"animatedead": "cleric,wizard",
"animateobjects": "artificer,bard,sorcerer,wizard,artificerrevisited",
"antilifeshell": "druid",
"antimagicfield": "cleric,wizard",
"antipathysympathy": "druid,wizard",
"arcaneeye": "artificer,wizard,artificer,artificerrevisited",
"arcanegate": "sorcerer,warlock,wizard",
"arcanelock": "artificer,wizard,artificer,artificerrevisited",
"armorofagathys": "warlock",
"armsofhadar": "warlock",
"astralprojection": "cleric,warlock,wizard",
"augury": "cleric",
"auraoflife": "paladin",
"auraofpurity": "paladin",
"auraofvitality": "paladin",
"awaken": "bard,druid",
"bane": "bard,cleric",
"banishingsmite": "paladin",
"banishment": "cleric,paladin,sorcerer,warlock,wizard",
"barkskin": "druid,ranger",
"beaconofhope": "cleric",
"beastbond": "druid,ranger",
"beastsense": "druid,ranger",
"bestowcurse": "bard,cleric,wizard",
"bigbyshand": "artificer,wizard,artificerrevisited",
"arcanehand": "wizard,artificerrevisited",
"bladebarrier": "cleric",
"bladeward": "bard,sorcerer,warlock,wizard",
"bless": "cleric,paladin",
"blight": "druid,sorcerer,warlock,wizard",
"blindingsmite": "paladin",
"blindnessdeafness": "bard,cleric,sorcerer,wizard",
"blink": "artificer,sorcerer,wizard,artificer,artificerrevisited",
"blur": "artificer,sorcerer,wizard,artificer,artificerrevisited",
"bonesoftheearth": "druid",
"boomingblade": "sorcerer,warlock,wizard",
"brandingsmite": "paladin",
"burninghands": "sorcerer,wizard",
"calllightning": "druid",
"calmemotions": "bard,cleric",
"catapult": "artificer,sorcerer,wizard",
"catnap": "artificer,bard,sorcerer,wizard",
"causefear": "warlock,wizard",
"ceremony": "cleric,paladin",
"chainlightning": "sorcerer,wizard",
"chaosbolt": "sorcerer",
"charmmonster": "bard,druid,sorcerer,warlock,wizard",
"charmperson": "bard,druid,sorcerer,warlock,wizard",
"chilltouch": "sorcerer,warlock,wizard",
"chromaticorb": "sorcerer,wizard",
"circleofdeath": "sorcerer,warlock,wizard",
"circleofpower": "paladin",
"clairvoyance": "bard,cleric,sorcerer,wizard",
"clone": "wizard",
"cloudofdaggers": "bard,sorcerer,warlock,wizard",
"cloudkill": "sorcerer,wizard",
"colorspray": "sorcerer,wizard",
"command": "cleric,paladin",
"commune": "cleric",
"communewithnature": "druid,ranger",
"compelledduel": "paladin",
"comprehendlanguages": "bard,sorcerer,warlock,wizard",
"compulsion": "bard",
"coneofcold": "sorcerer,wizard",
"confusion": "bard,druid,sorcerer,wizard",
"conjureanimals": "druid,ranger",
"conjurebarrage": "ranger",
"conjurecelestial": "cleric",
"conjureelemental": "druid,wizard",
"conjurefey": "druid,warlock",
"conjureminorelementals": "druid,wizard",
"conjurevolley": "ranger",
"conjurewoodlandbeings": "druid,ranger",
"contactotherplane": "warlock,wizard",
"contagion": "cleric,druid",
"contingency": "wizard",
"continualflame": "artificer,cleric,wizard,artificer,artificerrevisited",
"controlflames": "druid,sorcerer,wizard",
"controlwater": "cleric,druid,wizard",
"controlweather": "cleric,druid,wizard",
"controlwinds": "druid,sorcerer,wizard",
"cordonofarrows": "ranger",
"counterspell": "sorcerer,warlock,wizard",
"createbonfire": "artificer,druid,sorcerer,warlock,wizard",
"createfoodandwater": "artificer,cleric,paladin",
"createhomunculus": "wizard",
"createundead": "cleric,warlock,wizard",
"createordestroywater": "cleric,druid",
"creation": "artificer,sorcerer,wizard,artificerrevisited",
"crownofmadness": "bard,sorcerer,warlock,wizard",
"crownofstars": "sorcerer,warlock,wizard",
"crusadersmantle": "paladin",
"curewounds": "artificer,bard,cleric,druid,paladin,ranger,artificer,artificerrevisited",
"dancinglights": "artificer,bard,sorcerer,wizard,artificerrevisited",
"dansemacabre": "warlock,wizard",
"darkness": "sorcerer,warlock,wizard",
"darkvision": "artificer,druid,ranger,sorcerer,wizard,artificer,artificerrevisited",
"dawn": "cleric,wizard",
"daylight": "cleric,druid,paladin,ranger,sorcerer",
"deathward": "cleric,paladin,artificer",
"delayedblastfireball": "sorcerer,wizard",
"demiplane": "warlock,wizard",
"destructivewave": "paladin",
"detectevilandgood": "cleric,paladin",
"detectmagic": "artificer,bard,cleric,druid,paladin,ranger,sorcerer,wizard,artificerrevisited",
"detectpoisonanddisease": "cleric,druid,paladin,ranger",
"detectthoughts": "bard,sorcerer,wizard",
"dimensiondoor": "bard,sorcerer,warlock,wizard",
"disguiseself": "artificer,bard,sorcerer,wizard,artificer,artificerrevisited",
"disintegrate": "sorcerer,wizard",
"dispelevilandgood": "cleric,paladin",
"dispelmagic": "artificer,bard,cleric,druid,paladin,sorcerer,warlock,wizard,artificerrevisited",
"dissonantwhispers": "bard",
"distortvalue": "bard,sorcerer,warlock,wizard",
"divination": "cleric",
"divinefavor": "paladin",
"divineword": "cleric",
"dominatebeast": "druid,sorcerer",
"dominatemonster": "bard,sorcerer,warlock,wizard",
"dominateperson": "bard,sorcerer,wizard",
"dragonsbreath": "sorcerer,wizard",
"drawmijsinstantsummons": "wizard",
"instantsummons": "wizard",
"dream": "bard,warlock,wizard",
"druidgrove": "druid",
"druidcraft": "druid",
"dustdevil": "druid,sorcerer,wizard",
"earthtremor": "bard,druid,sorcerer,wizard",
"earthbind": "druid,sorcerer,warlock,wizard",
"earthquake": "cleric,druid,sorcerer",
"eldritchblast": "warlock",
"elementalbane": "artificer,druid,warlock,wizard",
"elementalweapon": "artificer,paladin,artificerrevisited",
"enemiesabound": "bard,sorcerer,warlock,wizard",
"enervation": "sorcerer,warlock,wizard",
"enhanceability": "artificer,bard,cleric,druid,sorcerer,artificer,artificerrevisited",
"enlargereduce": "artificer,sorcerer,wizard,artificer,artificerrevisited",
"ensnaringstrike": "ranger",
"entangle": "druid",
"enthrall": "bard,warlock",
"eruptingearth": "druid,sorcerer,wizard",
"etherealness": "bard,cleric,sorcerer,warlock,wizard",
"evardsblacktentacles": "wizard",
"blacktentacles": "wizard",
"expeditiousretreat": "artificer,sorcerer,warlock,wizard,artificer,artificerrevisited",
"eyebite": "bard,sorcerer,warlock,wizard",
"fabricate": "artificer,wizard,artificer,artificerrevisited",
"faeriefire": "artificer,bard,druid",
"falselife": "artificer,sorcerer,wizard,artificer,artificerrevisited",
"farstep": "sorcerer,warlock,wizard",
"fastfriends": "bard,cleric,wizard",
"fear": "bard,sorcerer,warlock,wizard",
"featherfall": "artificer,bard,sorcerer,wizard",
"feeblemind": "bard,druid,warlock,wizard",
"feigndeath": "bard,cleric,druid,wizard",
"findfamiliar": "wizard",
"findgreatersteed": "paladin",
"findsteed": "paladin",
"findtraps": "cleric,druid,ranger",
"findthepath": "bard,cleric,druid",
"fingerofdeath": "sorcerer,warlock,wizard",
"firebolt": "artificer,sorcerer,wizard,artificerrevisited",
"fireshield": "wizard",
"firestorm": "cleric,druid,sorcerer",
"fireball": "sorcerer,wizard",
"flamearrows": "artificer,druid,ranger,sorcerer,wizard",
"flameblade": "druid",
"flamestrike": "cleric",
"flamingsphere": "druid,wizard",
"fleshtostone": "warlock,wizard",
"fly": "artificer,sorcerer,warlock,wizard,artificer,artificerrevisited",
"fogcloud": "druid,ranger,sorcerer,wizard",
"forbiddance": "cleric",
"forcecage": "bard,warlock,wizard",
"foresight": "bard,druid,warlock,wizard",
"freedomofmovement": "artificer,bard,cleric,druid,ranger,artificer,artificerrevisited",
"friends": "bard,sorcerer,warlock,wizard",
"frostbite": "artificer,druid,sorcerer,warlock,wizard",
"gaseousform": "sorcerer,warlock,wizard,artificer,artificerrevisited",
"gate": "cleric,sorcerer,wizard",
"geas": "bard,cleric,druid,paladin,wizard",
"gentlerepose": "cleric,wizard",
"giantinsect": "druid",
"giftofgab": "bard,wizard",
"glibness": "bard,warlock",
"globeofinvulnerability": "sorcerer,wizard",
"glyphofwarding": "artificer,bard,cleric,wizard,artificer,artificerrevisited",
"goodberry": "druid,ranger",
"graspingvine": "druid,ranger",
"grease": "artificer,wizard,artificerrevisited",
"greaterinvisibility": "bard,sorcerer,wizard",
"greaterrestoration": "artificer,bard,cleric,druid,artificerrevisited",
"greenflameblade": "sorcerer,warlock,wizard",
"guardianoffaith": "cleric",
"guardianofnature": "druid,ranger",
"guardsandwards": "bard,wizard",
"guidance": "artificer,cleric,druid,artificerrevisited",
"guidingbolt": "cleric",
"gust": "druid,sorcerer,wizard",
"gustofwind": "druid,sorcerer,wizard",
"hailofthorns": "ranger",
"hallow": "cleric",
"hallucinatoryterrain": "bard,druid,warlock,wizard",
"harm": "cleric",
"haste": "artificer,sorcerer,wizard,artificer,artificerrevisited",
"heal": "cleric,druid",
"healingspirit": "druid,ranger",
"healingword": "bard,cleric,druid",
"heatmetal": "artificer,bard,druid,artificerrevisited",
"hellishrebuke": "warlock",
"heroesfeast": "cleric,druid",
"heroism": "bard,paladin",
"hex": "warlock",
"holdmonster": "bard,sorcerer,warlock,wizard",
"holdperson": "bard,cleric,druid,sorcerer,warlock,wizard",
"holyaura": "cleric",
"holyweapon": "cleric,paladin",
"hungerofhadar": "warlock",
"huntersmark": "ranger",
"hypnoticpattern": "bard,sorcerer,warlock,wizard",
"iceknife": "druid,sorcerer,wizard",
"icestorm": "druid,sorcerer,wizard",
"identify": "artificer,bard,wizard,artificerrevisited",
"illusorydragon": "wizard",
"illusoryscript": "bard,warlock,wizard",
"immolation": "sorcerer,wizard",
"imprisonment": "warlock,wizard",
"incendiarycloud": "sorcerer,wizard",
"incitegreed": "cleric,warlock,wizard",
"infernalcalling": "warlock,wizard",
"infestation": "druid,sorcerer,warlock,wizard",
"inflictwounds": "cleric",
"insectplague": "cleric,druid,sorcerer",
"investitureofflame": "druid,sorcerer,warlock,wizard",
"investitureofice": "druid,sorcerer,warlock,wizard",
"investitureofstone": "druid,sorcerer,warlock,wizard",
"investitureofwind": "druid,sorcerer,warlock,wizard",
"invisibility": "artificer,bard,sorcerer,warlock,wizard,artificer,artificerrevisited",
"invulnerability": "wizard",
"jimsglowingcoin": "wizard",
"jimsmagicmissile": "wizard",
"jump": "artificer,druid,ranger,sorcerer,wizard,artificer,artificerrevisited",
"knock": "bard,sorcerer,wizard",
"legendlore": "bard,cleric,wizard",
"leomundssecretchest": "artificer,wizard,artificer,artificerrevisited",
"leomundstinyhut": "bard,wizard",
"lesserrestoration": "artificer,bard,cleric,druid,paladin,ranger,artificer,artificerrevisited",
"levitate": "artificer,sorcerer,wizard,artificerrevisited",
"lifetransference": "cleric,wizard",
"light": "artificer,bard,cleric,sorcerer,wizard,artificerrevisited",
"lightningarrow": "ranger",
"lightningbolt": "sorcerer,wizard",
"lightninglure": "sorcerer,warlock,wizard",
"locateanimalsorplants": "bard,druid,ranger",
"locatecreature": "bard,cleric,druid,paladin,ranger,wizard",
"locateobject": "bard,cleric,druid,paladin,ranger,wizard",
"longstrider": "artificer,bard,druid,ranger,wizard,artificer,artificerrevisited",
"maddeningdarkness": "warlock,wizard",
"maelstrom": "druid",
"magearmor": "sorcerer,wizard",
"magehand": "artificer,bard,sorcerer,warlock,wizard,artificerrevisited",
"magiccircle": "cleric,paladin,warlock,wizard",
"magicjar": "wizard",
"magicmissile": "sorcerer,wizard",
"magicmouth": "artificer,bard,wizard,artificerrevisited",
"magicstone": "artificer,druid,warlock",
"magicweapon": "artificer,paladin,wizard,artificer,artificerrevisited",
"majorimage": "bard,sorcerer,warlock,wizard",
"masscurewounds": "bard,cleric,druid",
"massheal": "cleric",
"masshealingword": "cleric",
"masspolymorph": "bard,sorcerer,wizard",
"masssuggestion": "bard,sorcerer,warlock,wizard",
"maximiliansearthengrasp": "sorcerer,wizard",
"maze": "wizard",
"meldintostone": "cleric,druid",
"melfsacidarrow": "wizard",
"melfsminutemeteors": "sorcerer,wizard",
"acidarrow": "wizard",
"mending": "artificer,bard,cleric,druid,sorcerer,wizard,artificerrevisited",
"mentalprison": "sorcerer,warlock,wizard",
"message": "artificer,bard,sorcerer,wizard,artificerrevisited",
"meteorswarm": "sorcerer,wizard",
"mightyfortress": "wizard",
"mindblank": "bard,wizard",
"mindspike": "sorcerer,warlock,wizard",
"minorillusion": "bard,sorcerer,warlock,wizard",
"miragearcane": "bard,druid,wizard",
"mirrorimage": "sorcerer,warlock,wizard",
"mislead": "bard,wizard",
"mistystep": "sorcerer,warlock,wizard",
"modifymemory": "bard,wizard",
"moldearth": "druid,sorcerer,wizard",
"moonbeam": "druid",
"mordenkainensfaithfulhound": "artificer,wizard,artificer,artificerrevisited",
"motivationalspeech": "bard,cleric",
"faithfulhound": "wizard,artificer,artificerrevisited",
"mordenkainensmagnificentmansion": "bard,wizard",
"magnificentmansion": "bard,wizard",
"mordenkainensprivatesanctum": "artificer,wizard,artificer,artificerrevisited",
"mordenkainenssword": "bard,wizard",
"arcanesword": "bard,wizard",
"moveearth": "druid,sorcerer,wizard",
"negativeenergyflood": "warlock,wizard",
"nondetection": "bard,ranger,wizard",
"nystulsmagicaura": "wizard",
"arcanistsmagicaura": "wizard",
"otilukesfreezingsphere": "wizard",
"otilukesresilientsphere": "artificer,wizard,artificer,artificerrevisited",
"ottosirresistibledance": "bard,wizard",
"passwithouttrace": "druid,ranger",
"passwall": "wizard",
"phantasmalforce": "bard,sorcerer,wizard",
"phantasmalkiller": "wizard",
"phantomsteed": "wizard",
"planarally": "cleric",
"planarbinding": "bard,cleric,druid,wizard",
"planeshift": "cleric,druid,sorcerer,warlock,wizard",
"plantgrowth": "bard,druid,ranger",
"poisonspray": "artificer,druid,sorcerer,warlock,wizard,artificerrevisited",
"polymorph": "bard,druid,sorcerer,wizard",
"powerwordheal": "bard",
"powerwordkill": "bard,sorcerer,warlock,wizard",
"powerwordpain": "sorcerer,warlock,wizard",
"powerwordstun": "bard,sorcerer,warlock,wizard",
"prayerofhealing": "cleric",
"prestidigitation": "artificer,bard,sorcerer,warlock,wizard,artificerrevisited",
"primalsavagery": "druid",
"primordialward": "druid",
"prismaticspray": "sorcerer,wizard",
"prismaticwall": "wizard",
"produceflame": "druid",
"programmedillusion": "bard,wizard",
"projectimage": "bard,wizard",
"protectionfromenergy": "artificer,cleric,druid,ranger,sorcerer,wizard,artificer,artificerrevisited",
"protectionfromevilandgood": "cleric,paladin,warlock,wizard",
"protectionfrompoison": "artificer,cleric,druid,paladin,ranger,artificer,artificerrevisited",
"psychicscream": "bard,sorcerer,warlock,wizard",
"purifyfoodanddrink": "artificer,cleric,druid,paladin",
"pyrotechnics": "artificer,bard,sorcerer,wizard",
"raisedead": "bard,cleric,paladin",
"rarystelepathicbond": "wizard",
"rayofenfeeblement": "warlock,wizard",
"rayoffrost": "artificer,sorcerer,wizard,artificerrevisited",
"rayofsickness": "sorcerer,wizard",
"regenerate": "bard,cleric,druid",
"reincarnate": "druid",
"removecurse": "cleric,paladin,warlock,wizard",
"resistance": "artificer,cleric,druid,artificerrevisited",
"resurrection": "bard,cleric",
"reversegravity": "druid,sorcerer,wizard",
"revivify": "artificer,cleric,paladin,artificer,artificerrevisited",
"ropetrick": "artificer,wizard,artificer,artificerrevisited",
"sacredflame": "cleric",
"sanctuary": "artificer,cleric,artificer,artificerrevisited",
"scatter": "sorcerer,warlock,wizard",
"scorchingray": "sorcerer,wizard",
"scrying": "bard,cleric,druid,warlock,wizard",
"searingsmite": "paladin",
"seeinvisibility": "artificer,bard,sorcerer,wizard,artificerrevisited",
"seeming": "bard,sorcerer,wizard",
"sending": "bard,cleric,wizard",
"sequester": "wizard",
"shadowblade": "sorcerer,warlock,wizard",
"shadowofmoil": "warlock",
"shapewater": "druid,sorcerer,wizard",
"shapechange": "druid,wizard",
"shatter": "bard,sorcerer,warlock,wizard",
"shield": "sorcerer,wizard",
"shieldoffaith": "cleric,paladin,artificer,artificerrevisited",
"shillelagh": "druid",
"shockinggrasp": "artificer,sorcerer,wizard,artificerrevisited",
"sickeningradiance": "sorcerer,warlock,wizard",
"silence": "bard,cleric,ranger",
"silentimage": "bard,sorcerer,wizard",
"simulacrum": "wizard",
"skillempowerment": "artificer,bard,sorcerer,wizard",
"skywrite": "artificer,bard,druid,wizard",
"sleep": "bard,sorcerer,wizard",
"sleetstorm": "druid,sorcerer,wizard",
"slow": "sorcerer,wizard",
"snare": "artificer,druid,ranger,wizard",
"snillocssnowballswarm": "sorcerer,wizard",
"soulcage": "warlock,wizard",
"sparethedying": "artificer,cleric,artificerrevisited",
"speakwithanimals": "bard,druid,ranger",
"speakwithdead": "bard,cleric",
"speakwithplants": "bard,druid,ranger",
"spiderclimb": "artificer,sorcerer,warlock,wizard,artificer,artificerrevisited",
"spikegrowth": "druid,ranger",
"spiritguardians": "cleric",
"spiritualweapon": "cleric",
"staggeringsmite": "paladin",
"steelwindstrike": "ranger,wizard",
"stinkingcloud": "bard,sorcerer,wizard",
"stoneshape": "artificer,cleric,druid,wizard,artificer,artificerrevisited",
"stoneskin": "artificer,druid,ranger,sorcerer,wizard,artificer,artificerrevisited",
"stormofvengeance": "druid",
"stormsphere": "sorcerer,wizard",
"suggestion": "bard,sorcerer,warlock,wizard",
"summongreaterdemon": "warlock,wizard",
"summonlesserdemons": "warlock,wizard",
"sunbeam": "druid,sorcerer,wizard",
"sunburst": "druid,sorcerer,wizard",
"swiftquiver": "ranger",
"swordburst": "sorcerer,warlock,wizard",
"synapticstatic": "bard,sorcerer,warlock,wizard",
"symbol": "bard,cleric,wizard",
"tashashideouslaughter": "bard,wizard",
"hideouslaughter": "bard,wizard",
"telekinesis": "sorcerer,wizard",
"telepathy": "wizard",
"teleport": "bard,sorcerer,wizard",
"teleportationcircle": "bard,sorcerer,wizard",
"templeofthegods": "cleric",
"tensersfloatingdisk": "wizard",
"tensersfloatingdisc": "wizard",
"tenserstransformation": "wizard",
"floatingdisc": "wizard",
"thaumaturgy": "cleric",
"thornwhip": "artificer,druid,artificerrevisited",
"thunderstep": "sorcerer,warlock,wizard",
"thunderclap": "artificer,bard,druid,sorcerer,warlock,wizard",
"thunderoussmite": "paladin",
"thunderwave": "bard,druid,sorcerer,wizard",
"tidalwave": "druid,sorcerer,wizard",
"timestop": "sorcerer,wizard",
"tinyservant": "artificer,wizard",
"tollthedead": "cleric,warlock,wizard",
"tongues": "bard,cleric,sorcerer,warlock,wizard",
"transmuterock": "artificer,druid,wizard",
"transportviaplants": "druid",
"treestride": "druid,ranger",
"truepolymorph": "bard,warlock,wizard",
"trueresurrection": "cleric,druid",
"trueseeing": "bard,cleric,sorcerer,warlock,wizard",
"truestrike": "bard,sorcerer,warlock,wizard",
"tsunami": "druid",
"unseenservant": "bard,warlock,wizard",
"vampirictouch": "warlock,wizard",
"viciousmockery": "bard",
"vitriolicsphere": "sorcerer,wizard",
"walloffire": "druid,sorcerer,wizard",
"wallofforce": "wizard",
"wallofice": "wizard",
"walloflight": "sorcerer,warlock,wizard",
"wallofsand": "wizard",
"wallofstone": "artificer,druid,sorcerer,wizard,artificerrevisited",
"wallofthorns": "druid",
"wallofwater": "druid,sorcerer,wizard",
"wardingbond": "cleric",
"wardingwind": "bard,druid,sorcerer,wizard",
"waterbreathing": "artificer,druid,ranger,sorcerer,wizard,artificer,artificerrevisited",
"waterwalk": "artificer,cleric,druid,ranger,sorcerer,artificer,artificerrevisited",
"waterysphere": "druid,sorcerer,wizard",
"web": "artificer,sorcerer,wizard",
"weird": "wizard",
"whirlwind": "druid,sorcerer,wizard",
"windwalk": "druid",
"windwall": "druid,ranger",
"wish": "sorcerer,wizard",
"witchbolt": "sorcerer,warlock,wizard",
"wordofradiance": "cleric",
"wordofrecall": "cleric",
"wrathofnature": "druid,ranger",
"wrathfulsmite": "paladin",
"zephyrstrike": "ranger",
"zoneoftruth": "bard,cleric,paladin"
}

58
src/lang/de.json 100644
View File

@ -0,0 +1,58 @@
{
"CMPBrowser.compendiumBrowser": "Kompendium Browser",
"CMPBrowser.sortBy": "Sortiere anhand",
"CMPBrowser.generalSettings": "Allgemeine Einstellungen",
"CMPBrowser.allowSpellAcc": "Erlaubew Spielern den Zugriff auf den Zauber Browser",
"CMPBrowser.allowFeatAcc": "Allow Players Access to the feat browser",
"CMPBrowser.allowItemAcc": "Allow Players Access to the item browser",
"CMPBrowser.allowNpcAcc": "Erlaube Spielern den Zugriff auf den NSC Browser",
"CMPBrowser.compSettingsSpell": "Gegenstands Kompendium Einstellungen",
"CMPBrowser.compSettingsNpc": "NSC Kompendium Einstellungen",
"CMPBrowser.load": "Laden",
"CMPBrowser.castingTime": "Wirkungsdauer",
"CMPBrowser.spellType": "Zauberart",
"CMPBrowser.damageType": "Schadensart",
"CMPBrowser.UsesResources": "Uses Resources",
"CMPBrowser.GameMechanics": "Game Mechanics",
"CMPBrowser.ItemSubtype": "Item Subtype",
"CMPBrowser.MagicItems": "Magic Items",
"CMPBrowser.ItemsPacks": "Packs",
"CMPBrowser.ItemsPacksBurglar": "Burglar's Pack",
"CMPBrowser.ItemsPacksDiplomat": "Diplomat's Pack",
"CMPBrowser.ItemsPacksDungeoneer": "Dungeoneer's Pack",
"CMPBrowser.ItemsPacksEntertainer": "Entertainer's Pack",
"CMPBrowser.ItemsPacksExplorer": "Explorer's Pack",
"CMPBrowser.ItemsPacksMonsterHunter": "Monster Hunter's Pack",
"CMPBrowser.ItemsPacksPriest": "Priest's Pack",
"CMPBrowser.ItemsPacksScholar": "Scholar's Pack",
"CMPBrowser.artificer": "Artificer",
"CMPBrowser.barbarian": "Barbarian",
"CMPBrowser.bard": "Barde",
"CMPBrowser.cleric": "Kleriker",
"CMPBrowser.druid": "Druide",
"CMPBrowser.fighter": "Fighter",
"CMPBrowser.monk": "Monk",
"CMPBrowser.paladin": "Paladin",
"CMPBrowser.ranger": "Waldläufer",
"CMPBrowser.rogue": "Rogue",
"CMPBrowser.sorcerer": "Zauberer",
"CMPBrowser.warlock": "Hexenmeister",
"CMPBrowser.wizard": "Magier",
"CMPBrowser.general": "Allgemein",
"CMPBrowser.hasSpells": "Hat Zauber",
"CMPBrowser.hasLegAct": "Hat Legendäre Aktionen",
"CMPBrowser.hasLegRes": "Hat Legendäre Resistenz",
"CMPBrowser.dmgInteraction": "Schadensinteraktion",
"CMPBrowser.dmgDealt": "Schaden zugefügt",
"CMPBrowser.Tab.SpellBrowser": "Zauber Browser",
"CMPBrowser.Tab.FeatBrowser": "Feat Browser",
"CMPBrowser.Tab.ItemBrowser": "Item Browser",
"CMPBrowser.Tab.NPCBrowser": "NSC Browser",
"CMPBrowser.Tab.Settings": "Einstellungen",
"CMPBrowser.SETTING.Maxload.NAME": "Maximum load",
"CMPBrowser.SETTING.Maxload.HINT": "Maximum number of spells, feats, items, or NPCs to display; to see more use the filters. This setting is to allow manageing memory and server load.",
"CMPBrowser.LOADING.Message": "Loading...{numLoaded} {itemType}s",
"CMPBrowser.LOADED.Message": "Loaded {numLoaded} {itemType}s",
"CMPBrowser.LOADED.MaxLoaded": "(maximum displayed; to see more, use the filters)",
"CMPBrowser.Filters.ResetFilters": "Reset Filters"
}

82
src/lang/en.json 100644
View File

@ -0,0 +1,82 @@
{
"CMPBrowser": {
"compendiumBrowser": "Compendium Browser",
"sortBy": "Sort by",
"generalSettings": "General Settings",
"allowSpellAcc": "Allow Players Access to the spell browser",
"allowFeatAcc": "Allow Players Access to the feat browser",
"allowItemAcc": "Allow Players Access to the item browser",
"allowNpcAcc": "Allow Players Access to the npc browser",
"compSettingsSpell": "Item Compendium Settings",
"compSettingsNpc": "NPC Compendium Settings",
"load": "Load",
"castingTime": "Casting Time",
"spellType": "Spell Type",
"damageType": "Damage Type",
"UsesResources": "Uses Resources",
"GameMechanics": "Game Mechanics",
"ItemSubtype": "Item Subtype",
"MagicItems": "Magic Items",
"ItemsPacks": "Packs",
"ItemsPacksBurglar": "Burglar's Pack",
"ItemsPacksDiplomat": "Diplomat's Pack",
"ItemsPacksDungeoneer": "Dungeoneer's Pack",
"ItemsPacksEntertainer": "Entertainer's Pack",
"ItemsPacksExplorer": "Explorer's Pack",
"ItemsPacksMonsterHunter": "Monster Hunter's Pack",
"ItemsPacksPriest": "Priest's Pack",
"ItemsPacksScholar": "Scholar's Pack",
"general": "General",
"overall": "Overall Type",
"subfeature": "Subfeature Type",
"hasSpells": "Has Spells",
"hasLegAct": "Has Legendary Actions",
"hasLegRes": "Has Legendary Resistance",
"dmgInteraction": "Damage Interaction",
"dmgDealt": "Damage Dealt",
"Tab": {
"SpellBrowser": "Spells",
"FeatBrowser": "Features",
"ItemBrowser": "Items",
"NPCBrowser": "Actors",
"Settings": "Settings"
},
"SETTING": {
"Maxload.NAME": "Maximum load",
"Maxload.HINT": "Maximum number of spells, feats, items, or NPCs to display; to see more use the filters. This setting is to allow manageing memory and server load.",
"extraButtonsGlobal.NAME": "Globally Enable Buttons",
"extraButtonsGlobal.HINT": "Globally enable shortcut buttons to the browser that are added to sheets (Must re-open window for it to apply)",
"extraSheetButtons.NAME": "Enable Extra Sheet Buttons",
"extraSheetButtons.HINT": "Enable extra shortcut buttons that appear on PC sheets (Must re-open window for it to apply)",
"extraAdvancementButtons.NAME": "Enable Extra Advancement Buttons",
"extraAdvancementButtons.HINT": "Enable extra shortcut buttons that appear on advancement windows (Must re-open window for it to apply)",
"bannersGlobal.NAME": "Enable Banners - Global",
"bannersGlobal.HINT": "Enable Banners for missing key features on PC sheets for all players",
"bannersLocal.NAME": "Enable Banners - Local",
"bannersLocal.HINT": "Enable Banners for missing key features on PC sheets for self"
},
"LOADING": {
"Message": "Loading..."
},
"LOADED": {
"Message": {
"feat": "Loaded {numLoaded} feats",
"item": "Loaded {numLoaded} items",
"npc": "Loaded {numLoaded} npcs",
"spell": "Loaded {numLoaded} spells"
},
"MaxLoaded": "(maximum displayed; to see more, use the filters)"
},
"ToolTip": {
"Feats": "Find Feats",
"Spells": "Find Spells",
"Features": "Find Features"
},
"FindA": {
"race": "Missing a Race, click to open list",
"background": "Missing a Background, click to open list",
"class": "Missing a Class, click to open list"
},
"Filters.ResetFilters": "Reset Filters"
}
}

58
src/lang/es.json 100644
View File

@ -0,0 +1,58 @@
{
"CMPBrowser.compendiumBrowser": "Compendium Browser",
"CMPBrowser.sortBy": "Ordenar por",
"CMPBrowser.generalSettings": "Opciones generales",
"CMPBrowser.allowSpellAcc": "Permitir a los jugadores el acceso al navegador de conjuros",
"CMPBrowser.allowFeatAcc": "Allow Players Access to the feat browser",
"CMPBrowser.allowItemAcc": "Allow Players Access to the item browser",
"CMPBrowser.allowNpcAcc": "Permitir a los jugadores el acceso al navegador de NPCs",
"CMPBrowser.compSettingsSpell": "Opciones del compendio de objetos",
"CMPBrowser.compSettingsNpc": "Opciones del compendio de NPCs",
"CMPBrowser.load": "Cargar",
"CMPBrowser.castingTime": "Tiempo de lanzamiento",
"CMPBrowser.spellType": "Tipo de conjuro",
"CMPBrowser.damageType": "Tipo de daño",
"CMPBrowser.UsesResources": "Uses Resources",
"CMPBrowser.GameMechanics": "Game Mechanics",
"CMPBrowser.ItemSubtype": "Item Subtype",
"CMPBrowser.MagicItems": "Magic Items",
"CMPBrowser.ItemsPacks": "Packs",
"CMPBrowser.ItemsPacksBurglar": "Burglar's Pack",
"CMPBrowser.ItemsPacksDiplomat": "Diplomat's Pack",
"CMPBrowser.ItemsPacksDungeoneer": "Dungeoneer's Pack",
"CMPBrowser.ItemsPacksEntertainer": "Entertainer's Pack",
"CMPBrowser.ItemsPacksExplorer": "Explorer's Pack",
"CMPBrowser.ItemsPacksMonsterHunter": "Monster Hunter's Pack",
"CMPBrowser.ItemsPacksPriest": "Priest's Pack",
"CMPBrowser.ItemsPacksScholar": "Scholar's Pack",
"CMPBrowser.artificer": "Artificiero",
"CMPBrowser.barbarian": "Barbarian",
"CMPBrowser.bard": "Bardo",
"CMPBrowser.cleric": "Clérigo",
"CMPBrowser.druid": "Druida",
"CMPBrowser.fighter": "Guerrero",
"CMPBrowser.monk": "Monje",
"CMPBrowser.paladin": "Paladín",
"CMPBrowser.ranger": "Explorador",
"CMPBrowser.rogue": "Pícaro",
"CMPBrowser.sorcerer": "Hechicero",
"CMPBrowser.warlock": "Brujo",
"CMPBrowser.wizard": "Mago",
"CMPBrowser.general": "General",
"CMPBrowser.hasSpells": "Tiene conjuros",
"CMPBrowser.hasLegAct": "Tiene acciones legendarias",
"CMPBrowser.hasLegRes": "Tiene resistencia legendaria",
"CMPBrowser.dmgInteraction": "Interacción con el daño",
"CMPBrowser.dmgDealt": "Daño infligido",
"CMPBrowser.Tab.SpellBrowser": "Conjuros",
"CMPBrowser.Tab.FeatBrowser": "Rasgos de clase",
"CMPBrowser.Tab.ItemBrowser": "Objetos",
"CMPBrowser.Tab.NPCBrowser": "NPCs",
"CMPBrowser.Tab.Settings": "Opciones",
"CMPBrowser.SETTING.Maxload.NAME": "Maximum load",
"CMPBrowser.SETTING.Maxload.HINT": "Maximum number of spells, feats, items, or NPCs to display; to see more use the filters. This setting is to allow manageing memory and server load.",
"CMPBrowser.LOADING.Message": "Loading...{numLoaded} {itemType}s",
"CMPBrowser.LOADED.Message": "Loaded {numLoaded} {itemType}s",
"CMPBrowser.LOADED.MaxLoaded": "(maximum displayed; to see more, use the filters)",
"CMPBrowser.Filters.ResetFilters": "Reset Filters"
}

58
src/lang/fr.json 100644
View File

@ -0,0 +1,58 @@
{
"CMPBrowser.compendiumBrowser": "Recherche dans les Compendium",
"CMPBrowser.sortBy": "Trié par",
"CMPBrowser.generalSettings": "Paramètres généraux",
"CMPBrowser.allowSpellAcc": "Autoriser les joueurs à accéder aux listes de sorts",
"CMPBrowser.allowFeatAcc": "Allow Players Access to the feat browser",
"CMPBrowser.allowItemAcc": "Allow Players Access to the item browser",
"CMPBrowser.allowNpcAcc": "Autoriser les joueurs à accéder aux listes de PNJ",
"CMPBrowser.compSettingsSpell": "Paramètres de compendium de sorts",
"CMPBrowser.compSettingsNpc": "Paramètres de compendium de PNJ",
"CMPBrowser.load": "Charger",
"CMPBrowser.castingTime": "Durée d'incantation",
"CMPBrowser.spellType": "Type de sort",
"CMPBrowser.damageType": "Type de dégâts",
"CMPBrowser.UsesResources": "Uses Resources",
"CMPBrowser.GameMechanics": "Game Mechanics",
"CMPBrowser.ItemSubtype": "Item Subtype",
"CMPBrowser.MagicItems": "Magic Items",
"CMPBrowser.ItemsPacks": "Packs",
"CMPBrowser.ItemsPacksBurglar": "Burglar's Pack",
"CMPBrowser.ItemsPacksDiplomat": "Diplomat's Pack",
"CMPBrowser.ItemsPacksDungeoneer": "Dungeoneer's Pack",
"CMPBrowser.ItemsPacksEntertainer": "Entertainer's Pack",
"CMPBrowser.ItemsPacksExplorer": "Explorer's Pack",
"CMPBrowser.ItemsPacksMonsterHunter": "Monster Hunter's Pack",
"CMPBrowser.ItemsPacksPriest": "Priest's Pack",
"CMPBrowser.ItemsPacksScholar": "Scholar's Pack",
"CMPBrowser.artificer": "Artificer",
"CMPBrowser.barbarian": "Barbarian",
"CMPBrowser.bard": "Barde",
"CMPBrowser.cleric": "Clerc",
"CMPBrowser.druid": "Druide",
"CMPBrowser.fighter": "Fighter",
"CMPBrowser.monk": "Monk",
"CMPBrowser.paladin": "Paladin",
"CMPBrowser.ranger": "Rôdeur",
"CMPBrowser.rogue": "Rogue",
"CMPBrowser.sorcerer": "Sorcier",
"CMPBrowser.warlock": "Ensorceleur",
"CMPBrowser.wizard": "Magicien",
"CMPBrowser.general": "Général",
"CMPBrowser.hasSpells": "à des Sorts",
"CMPBrowser.hasLegAct": "à des Actions Légendaires",
"CMPBrowser.hasLegRes": "à des Resistances Légendaires",
"CMPBrowser.dmgInteraction": "Spécificité des dégâts",
"CMPBrowser.dmgDealt": "Type de dégats",
"CMPBrowser.Tab.SpellBrowser": "Recherche de sorts",
"CMPBrowser.Tab.FeatBrowser": "Feat Browser",
"CMPBrowser.Tab.ItemBrowser": "Item Browser",
"CMPBrowser.Tab.NPCBrowser": "Recherche de PNJ",
"CMPBrowser.Tab.Settings": "Paramétrages",
"CMPBrowser.SETTING.Maxload.NAME": "Maximum load",
"CMPBrowser.SETTING.Maxload.HINT": "Maximum number of spells, feats, items, or NPCs to display; to see more use the filters. This setting is to allow manageing memory and server load.",
"CMPBrowser.LOADING.Message": "Loading...{numLoaded} {itemType}s",
"CMPBrowser.LOADED.Message": "Loaded {numLoaded} {itemType}s",
"CMPBrowser.LOADED.MaxLoaded": "(maximum displayed; to see more, use the filters)",
"CMPBrowser.Filters.ResetFilters": "Reset Filters"
}

58
src/lang/ja.json 100644
View File

@ -0,0 +1,58 @@
{
"CMPBrowser.compendiumBrowser": "辞典ブラウザ",
"CMPBrowser.sortBy": "並び替え",
"CMPBrowser.generalSettings": "一般設定",
"CMPBrowser.allowSpellAcc": "プレイヤーに呪文辞典の使用を許可する。",
"CMPBrowser.allowFeatAcc": "Allow Players Access to the feat browser",
"CMPBrowser.allowItemAcc": "Allow Players Access to the item browser",
"CMPBrowser.allowNpcAcc": "プレイヤーにNPC辞典の使用を許可する。",
"CMPBrowser.compSettingsSpell": "呪文辞典設定",
"CMPBrowser.compSettingsNpc": "NPC辞典設定",
"CMPBrowser.load": "追加",
"CMPBrowser.castingTime": "発動時間",
"CMPBrowser.spellType": "呪文種別",
"CMPBrowser.damageType": "ダメージ種別",
"CMPBrowser.UsesResources": "Uses Resources",
"CMPBrowser.GameMechanics": "Game Mechanics",
"CMPBrowser.ItemSubtype": "Item Subtype",
"CMPBrowser.MagicItems": "Magic Items",
"CMPBrowser.ItemsPacks": "Packs",
"CMPBrowser.ItemsPacksBurglar": "Burglar's Pack",
"CMPBrowser.ItemsPacksDiplomat": "Diplomat's Pack",
"CMPBrowser.ItemsPacksDungeoneer": "Dungeoneer's Pack",
"CMPBrowser.ItemsPacksEntertainer": "Entertainer's Pack",
"CMPBrowser.ItemsPacksExplorer": "Explorer's Pack",
"CMPBrowser.ItemsPacksMonsterHunter": "Monster Hunter's Pack",
"CMPBrowser.ItemsPacksPriest": "Priest's Pack",
"CMPBrowser.ItemsPacksScholar": "Scholar's Pack",
"CMPBrowser.artificer": "Artificer",
"CMPBrowser.barbarian": "Barbarian",
"CMPBrowser.bard": "バード",
"CMPBrowser.cleric": "クレリック",
"CMPBrowser.druid": "ドルイド",
"CMPBrowser.fighter": "Fighter",
"CMPBrowser.monk": "Monk",
"CMPBrowser.paladin": "パラディン",
"CMPBrowser.ranger": "レンジャー",
"CMPBrowser.rogue": "Rogue",
"CMPBrowser.sorcerer": "ソーサラー",
"CMPBrowser.warlock": "ウォーロック",
"CMPBrowser.wizard": "ウィザード",
"CMPBrowser.general": "一般",
"CMPBrowser.hasSpells": "術者",
"CMPBrowser.hasLegAct": "伝説的アクション所持",
"CMPBrowser.hasLegRes": "伝説的抵抗所持",
"CMPBrowser.dmgInteraction": "ダメージ関連",
"CMPBrowser.dmgDealt": "与えるダメージ種別",
"CMPBrowser.Tab.SpellBrowser": "呪文ブラウザ",
"CMPBrowser.Tab.FeatBrowser": "Feat Browser",
"CMPBrowser.Tab.ItemBrowser": "Item Browser",
"CMPBrowser.Tab.NPCBrowser": "NPCブラウザ",
"CMPBrowser.Tab.Settings": "設定",
"CMPBrowser.SETTING.Maxload.NAME": "Maximum load",
"CMPBrowser.SETTING.Maxload.HINT": "Maximum number of spells, feats, items, or NPCs to display; to see more use the filters. This setting is to allow manageing memory and server load.",
"CMPBrowser.LOADING.Message": "Loading...{numLoaded} {itemType}s",
"CMPBrowser.LOADED.Message": "Loaded {numLoaded} {itemType}s",
"CMPBrowser.LOADED.MaxLoaded": "(maximum displayed; to see more, use the filters)",
"CMPBrowser.Filters.ResetFilters": "Reset Filters"
}

View File

@ -0,0 +1,58 @@
{
"CMPBrowser.compendiumBrowser": "Navegador de Compêndio",
"CMPBrowser.sortBy": "Classificar por",
"CMPBrowser.generalSettings": "Configurações Gerais",
"CMPBrowser.allowSpellAcc": "Permite o acesso dos jogadores ao navegador de Magias",
"CMPBrowser.allowFeatAcc": "Permite o acesso dos jogadores ao navegador de Características",
"CMPBrowser.allowItemAcc": "Permite o acesso dos jogadores ao navegador de Itens",
"CMPBrowser.allowNpcAcc": "Permite o acesso dos jogadores ao navegador de NPCs",
"CMPBrowser.compSettingsSpell": "Configuração de Compêndio de Itens",
"CMPBrowser.compSettingsNpc": "Configuração de Compêndio de NPCs",
"CMPBrowser.load": "Carregar",
"CMPBrowser.castingTime": "Custo de Ativação",
"CMPBrowser.spellType": "Tipo da Magia",
"CMPBrowser.damageType": "Tipo de Dano",
"CMPBrowser.UsesResources": "Usa Recursos",
"CMPBrowser.GameMechanics": "Mecânicas do Jogo",
"CMPBrowser.ItemSubtype": "Tipo do Item",
"CMPBrowser.MagicItems": "Itens Mágicos",
"CMPBrowser.ItemsPacks": "Kits de Equipamentos",
"CMPBrowser.ItemsPacksBurglar": "Kit de Assaltante",
"CMPBrowser.ItemsPacksDiplomat": "Kit de Diplomata",
"CMPBrowser.ItemsPacksDungeoneer": "Kit de Explorador",
"CMPBrowser.ItemsPacksEntertainer": "Kit de Artista",
"CMPBrowser.ItemsPacksExplorer": "Kit de Aventureiro",
"CMPBrowser.ItemsPacksMonsterHunter": "Monster Hunter's Pack",
"CMPBrowser.ItemsPacksPriest": "Kit de Sacerdote",
"CMPBrowser.ItemsPacksScholar": "Kit de Erudito",
"CMPBrowser.artificer": "Artífice",
"CMPBrowser.barbarian": "Bárbaro",
"CMPBrowser.bard": "Bardo",
"CMPBrowser.cleric": "Clérigo",
"CMPBrowser.druid": "Druida",
"CMPBrowser.fighter": "Guerreiro",
"CMPBrowser.monk": "Monge",
"CMPBrowser.paladin": "Paladino",
"CMPBrowser.ranger": "Guardião",
"CMPBrowser.rogue": "Ladino",
"CMPBrowser.sorcerer": "Feiticeiro",
"CMPBrowser.warlock": "Bruxo",
"CMPBrowser.wizard": "Mago",
"CMPBrowser.general": "Geral",
"CMPBrowser.hasSpells": "Tem Magias",
"CMPBrowser.hasLegAct": "Tem Ações Lendárias",
"CMPBrowser.hasLegRes": "Tem Resistência Lendária",
"CMPBrowser.dmgInteraction": "Interação do Dano",
"CMPBrowser.dmgDealt": "Dano Causado",
"CMPBrowser.Tab.SpellBrowser": "Magias",
"CMPBrowser.Tab.FeatBrowser": "Características",
"CMPBrowser.Tab.ItemBrowser": "Itens",
"CMPBrowser.Tab.NPCBrowser": "Atores",
"CMPBrowser.Tab.Settings": "Configurações",
"CMPBrowser.SETTING.Maxload.NAME": "Capacidade máxima",
"CMPBrowser.SETTING.Maxload.HINT": "Número máximo de magias, características, itens ou NPCs a serem exibidos; para ver mais use os filtros. Essa configuração é usada para gerenciar memória e capacidade do servidor.",
"CMPBrowser.LOADING.Message": "Carregando...{numLoaded} {itemType}s",
"CMPBrowser.LOADED.Message": "{numLoaded} {itemType}s carregados(as)",
"CMPBrowser.LOADED.MaxLoaded": "(máximo exibido; para ver mais, use os filtros)",
"CMPBrowser.Filters.ResetFilters": "Redefinir Filtros"
}

68
src/module.json 100644
View File

@ -0,0 +1,68 @@
{
"id": "compendium-browser",
"title": "Compendium Browser",
"description": "Easily browse and filter spells, feats, items, and npcs loaded from compendiums!",
"authors": [
{
"name": "Matheus Clemente",
"discord": "mclemente#5524"
}
],
"url": "This is auto replaced",
"readme": "https://github.com/mclemente/compendium-browser/blob/master/README.md",
"bugs": "https://github.com/mclemente/compendium-browser/issues",
"changelog": "https://github.com/mclemente/compendium-browser/blob/master/Patchnotes.md",
"version": "This is auto replaced",
"compatibility": {
"minimum": "11",
"verified": "11"
},
"esmodules": ["module/compendium-browser.js"],
"styles": ["styles/compendium-browser.css"],
"languages": [
{
"lang": "en",
"name": "English",
"path": "lang/en.json"
},
{
"lang": "ja",
"name": "Japanese",
"path": "lang/ja.json"
},
{
"lang": "fr",
"name": "French (FRANCE)",
"path": "lang/fr.json"
},
{
"lang": "pt-BR",
"name": "Português (Brasil)",
"path": "lang/pt-BR.json"
},
{
"lang": "es",
"name": "Español",
"path": "lang/es.json"
},
{
"lang": "de",
"name": "Deutsch",
"path": "lang/de.json"
}
],
"relationships": {
"systems": [{
"id": "dnd5e",
"type": "system",
"compatibility": {
"minimum": "3.0.0",
"verified": "3.0.3"
}
}],
"requires": [],
"conflicts": []
},
"manifest": "This is auto replaced",
"download": "This is auto replaced"
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,21 @@
// SPDX-FileCopyrightText: 2022 Johannes Loher
//
// SPDX-License-Identifier: MIT
export async function preloadTemplates() {
const templatePaths = [
"modules/compendium-browser/templates/spell-browser.html",
"modules/compendium-browser/templates/spell-browser-list.html",
"modules/compendium-browser/templates/npc-browser.html",
"modules/compendium-browser/templates/npc-browser-list.html",
"modules/compendium-browser/templates/feat-browser.html",
"modules/compendium-browser/templates/feat-browser-list.html",
"modules/compendium-browser/templates/item-browser.html",
"modules/compendium-browser/templates/item-browser-list.html",
"modules/compendium-browser/templates/filter-container.html",
"modules/compendium-browser/templates/settings.html",
"modules/compendium-browser/templates/loading.html",
];
return loadTemplates(templatePaths);
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,82 @@
export function registerSettings() {
game.compendiumBrowser.readCompendiums = {
loadedSpellCompendium: {},
loadedNpcCompendium: {},
};
for (const compendium of game.packs) {
if (compendium.documentName === "Item") {
game.compendiumBrowser.readCompendiums.loadedSpellCompendium[compendium.collection] = {
load: true,
name: `${compendium.metadata.label} (${compendium.collection})`,
};
}
if (compendium.documentName === "Actor") {
game.compendiumBrowser.readCompendiums.loadedNpcCompendium[compendium.collection] = {
load: true,
name: `${compendium.metadata.label} (${compendium.collection})`,
};
}
}
// creating game setting container
game.settings.register("compendium-browser", "settings", {
name: "Compendium Browser Settings",
hint: "Settings to exclude packs from loading and visibility of the browser",
default: game.compendiumBrowser.readCompendiums,
type: Object,
scope: "world"
});
game.settings.register("compendium-browser", "maxload", {
name: game.i18n.localize("CMPBrowser.SETTING.Maxload.NAME"),
hint: game.i18n.localize("CMPBrowser.SETTING.Maxload.HINT"),
scope: "world",
config: true,
default: 600,
type: Number,
range: {
// If range is specified, the resulting setting will be a range slider
min: 200,
max: 2000,
step: 100,
},
});
game.settings.register("compendium-browser", "extraButtonsGlobal", {
name: game.i18n.localize("CMPBrowser.SETTING.extraButtonsGlobal.NAME"),
hint: game.i18n.localize("CMPBrowser.SETTING.extraButtonsGlobal.HINT"),
scope: "world",
config: true,
default: true,
type: Boolean,
});
game.settings.register("compendium-browser", "extraSheetButtons", {
name: game.i18n.localize("CMPBrowser.SETTING.extraSheetButtons.NAME"),
hint: game.i18n.localize("CMPBrowser.SETTING.extraSheetButtons.HINT"),
scope: "client",
config: true,
default: true,
type: Boolean,
});
game.settings.register("compendium-browser", "extraAdvancementButtons", {
name: game.i18n.localize("CMPBrowser.SETTING.extraAdvancementButtons.NAME"),
hint: game.i18n.localize("CMPBrowser.SETTING.extraAdvancementButtons.HINT"),
scope: "client",
config: true,
default: true,
type: Boolean,
});
game.settings.register("compendium-browser", "bannersGlobal", {
name: game.i18n.localize("CMPBrowser.SETTING.bannersGlobal.NAME"),
hint: game.i18n.localize("CMPBrowser.SETTING.bannersGlobal.HINT"),
scope: "world",
config: true,
default: true,
type: Boolean,
});
game.settings.register("compendium-browser", "bannersLocal", {
name: game.i18n.localize("CMPBrowser.SETTING.bannersLocal.NAME"),
hint: game.i18n.localize("CMPBrowser.SETTING.bannersLocal.HINT"),
scope: "client",
config: true,
default: true,
type: Boolean,
});
}

View File

@ -0,0 +1,359 @@
@color_1: #bbb;
#compendium {
.directory-footer {
.compendium-browser-btn {
margin-top: 5px;
}
display: block;
}
}
.compendium-browser {
overflow-y: hidden !important;
max-width: 1100px;
max-height: 90vh;
min-width: 630px;
min-height: 500px;
.window-content {
overflow-y: hidden !important;
height: 100%;
.parent {
overflow-y: hidden !important;
height: 100%;
.content {
overflow-y: hidden !important;
height: calc(100% - 2em);
.tab {
overflow-y: hidden !important;
height: 100%;
.browser {
overflow-y: hidden !important;
height: 100%;
ul {
overflow-y: auto;
overflow-x: hidden;
height: 100%;
}
}
.settings {
overflow-y: auto;
height: 100%;
}
}
}
}
}
.tabs {
max-height: 2em;
border-bottom: 1px solid var(--color-border-light-primary);
}
.tabContainer {
height: calc(100% - 2em);
.tab {
width: 100%;
height: 100%;
overflow: scroll;
}
}
.control-area {
position: sticky;
display: block;
min-width: 250px;
max-width: 45%;
width: 350px;
height: 100%;
padding-right: 5px;
overflow: auto;
button {
background: rgba(0, 0, 0, 0.05);
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding: 2px;
}
.filtercontainer {
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding: 2px;
h3 {
margin: 0;
cursor: pointer;
}
dl {
margin: 5px 0;
}
div {
margin: 5px 0;
}
dt {
display: inline-block;
width: 40%;
padding-left: 5px;
}
dd {
display: inline-block;
width: 58%;
margin-left: 0;
select {
width: 100%;
}
}
.multiselect {
border: 1px solid #bbb;
border-radius: 3px;
vertical-align: middle;
line-height: 32px;
margin: 2px 0;
label {
padding: 5px;
}
input {
vertical-align: middle;
}
}
.small-input {
width: calc(100% - 44px);
height: 27px;
background: rgba(0, 0, 0, 0.05);
border: 1px solid #444;
border-radius: 3px;
padding: 0 3px;
text-overflow: ellipsis;
}
.small-select {
width: 40px;
}
}
}
.list-area {
position: sticky;
display: flex;
min-width: 250px;
max-width: 55%;
width: 400px;
height: 100%;
padding-right: 5px;
.loading {
flex: 0;
text-align: center;
}
}
.browser {
height: 100%;
overflow-y: hidden !important;
.window-content {
overflow-y: hidden !important;
}
ul {
float: right;
display: block;
min-width: 335px;
margin: 0;
height: 100%;
overflow: auto;
padding-left: 5px;
.filter-tags {
display: none;
}
li {
span {
white-space: nowrap;
overflow: hidden;
}
.spell-tags {
span.negative {
color: @color_1;
}
}
.item-name {
span {
white-space: break-spaces;
height: inherit;
display: block;
}
}
.feat-tags {
span {
white-space: break-spaces;
height: inherit;
display: block;
}
}
}
}
.spacer {
display: inline-block;
min-width: 5px;
}
.spacer-large {
display: inline-block;
min-width: 15px;
}
}
.item-browser {
li {
cursor: default;
vertical-align: middle;
line-height: 16px;
margin: 2px 0;
height: 32px;
.item-image {
max-width: 32px;
height: 32px;
}
.item-name {
padding-left: 5px;
flex: 2;
}
.feat-tags {
text-align: right;
margin-right: 3px;
margin-left: 3px;
text-transform: capitalize;
height: 32px;
}
.item-tags {
text-align: right;
margin-right: 3px;
margin-left: 3px;
text-transform: capitalize;
height: 32px;
}
}
}
.feat-browser {
li {
cursor: default;
vertical-align: middle;
line-height: 16px;
margin: 2px 0;
height: 32px;
.item-image {
max-width: 32px;
height: 32px;
}
.item-name {
padding-left: 5px;
flex: 2;
}
.feat-tags {
text-align: right;
margin-right: 3px;
margin-left: 3px;
text-transform: capitalize;
height: 32px;
}
.item-tags {
text-align: right;
margin-right: 3px;
margin-left: 3px;
text-transform: capitalize;
height: 32px;
}
}
}
.spell-browser {
li {
cursor: default;
vertical-align: middle;
line-height: 16px;
margin: 2px 0;
height: 32px;
.item-image {
max-width: 32px;
height: 32px;
}
.item-name {
padding-left: 5px;
flex: 2;
}
.feat-tags {
text-align: right;
margin-right: 3px;
margin-left: 3px;
text-transform: capitalize;
height: 32px;
}
.item-tags {
text-align: right;
margin-right: 3px;
margin-left: 3px;
text-transform: capitalize;
height: 32px;
}
}
.spell {
.spell-level {
text-align: center;
font-weight: 900;
max-width: 18px;
height: 32px;
}
.spell-tags {
text-align: right;
margin-right: 3px;
font-weight: 900;
max-width: 100px;
height: 32px;
}
}
}
.npc-browser {
.npc {
cursor: default;
vertical-align: middle;
line-height: 64px;
margin: 4px 0;
.npc-image {
max-width: 64px;
height: 64px;
img {
width: 64px;
height: 64px;
border: none;
object-fit: contain;
}
}
.npc-line {
line-height: 25px;
padding: 9px 0 5px 5px;
}
.npc-name {
font-weight: bold;
font-size: 16px;
}
.cr {
display: inline-block;
width: 55px;
}
.size {
display: inline-block;
width: 75px;
}
.type {
display: inline-block;
}
}
}
.settings {
.settings-group {
border: 1px solid #bbb;
border-radius: 5px;
margin-top: 5px;
padding: 2px;
h3 {
margin: 0;
cursor: pointer;
}
label {
display: block;
}
h4 {
display: inline-block;
vertical-align: middle;
height: 100%;
}
}
}
}

View File

@ -0,0 +1,25 @@
{{#each listItems as |feat id|}}
<li class="feat flexrow draggable" data-entry-compendium="{{feat.compendium}}" data-entry-id="{{id}}">
<div class="item-image">
<img
class=""
data-src="{{feat.img}}"
data-tooltip="{{feat.name}}"
data-tooltip-direction="UP"
width="32"
height="32"
/>
</div>
<div class="item-name">
<span class="item-edit"
><a data-tooltip="({{feat.compendium}})" data-tooltip-direction="UP">{{feat.name}}</a></span
>
</div>
<div class="feat-tags">
<span data-tooltip="Class Requirement" data-tooltip-direction="UP">{{feat.classRequirementString}}</span>
</div>
<div class="filter-tags">
<input type="hidden" name="class" value="{{feat.classRequirementString}}" />
</div>
</li>
{{/each}}

View File

@ -0,0 +1,34 @@
<div class="feat-browser browser flexrow">
<div class="control-area">
<div class="filtercontainer" id="tagfilter">
<div class="filter" data-type="text" data-path="name">
<input
class=""
name="textFilter"
type="text"
value=""
data-dtype="String"
placeholder="{{localize
'Name'}}"
/>
</div>
<dl id="sorter">
<dt>{{localize "CMPBrowser.sortBy"}}:</dt>
<dd>
<select name="sortorder">
<option value="true" selected>{{localize "Name"}}</option>
<option value="false">{{localize "ITEM.TypeClass"}}</option>
</select>
</dd>
</dl>
<button id="reset-feat-filter">{{localize "CMPBrowser.Filters.ResetFilters"}}</button>
</div>
{{> "modules/compendium-browser/templates/filter-container.html" filters=featFilters}}
</div>
<div class="list-area flexcol">
<ul id="CBFeats">
{{> "modules/compendium-browser/templates/feat-browser-list.html" feats=items}}
</ul>
<span class="loading" id="CBFeatsMessage" style="flex: 0"></span>
</div>
</div>

View File

@ -0,0 +1,79 @@
{{#each filters.registeredFilterCategories as |cat key|}}
<div class="filtercontainer" id="{{key}}">
<h3>{{cat.label}}</h3>
<div class="filters">
{{#each cat.filters as |filter key|}}
<div
class="filter"
id="{{cat.labelId}}-{{filter.labelId}}"
data-path="{{filter.path}}"
data-type="{{filter.type}}"
data-valIsArray="{{filter.valIsArray}}"
>
{{#if filter.istext}}
<dt>{{filter.label}}</dt>
<dd>
{{#if filter.possibleValues}}
<select>
<option value="" selected></option>
{{#each filter.possibleValues as |label val|}}
<option value="{{val}}">{{label}}</option>
{{/each}}
</select>
{{else}}
<input type="text" />
{{/if}}
</dd>
{{/if}} {{#if filter.isbool}}
<dl>
<dt>{{filter.label}}</dt>
<dd>
<select>
<option value="null" selected></option>
<option value="true">{{localize "Yes"}}</option>
<option value="false">{{localize "No"}}</option>
</select>
</dd>
</dl>
{{/if}} {{#if filter.isselect}}
<dl>
<dt>{{filter.label}}</dt>
<dd>
<select>
<option value="null" selected></option>
{{#each filter.possibleValues as |label val|}}
<option value="{{val}}">{{label}}</option>
{{/each}}
</select>
</dd>
</dl>
{{/if}} {{#if filter.ismultiSelect}}
<div class="multiselect">
<label>{{filter.label}}</label>
<dl>
{{#each filter.possibleValues as |label val|}}
<dt><label>{{label}}</label></dt>
<dd><input type="checkbox" data-value="{{val}}" /></dd>
{{/each}}
</dl>
</div>
{{/if}} {{#if filter.isnumberCompare}}
<div class="numberCompare">
<dt>{{filter.label}}</dt>
<dd>
<select class="small-select">
<option value="null" selected></option>
<option value="=">=</option>
<option value="<">&lt;</option>
<option value=">">&gt;</option>
</select>
<input class="small-input" type="number" />
</dd>
</div>
{{/if}}
</div>
{{/each}}
</div>
</div>
{{/each}}

View File

@ -0,0 +1,25 @@
{{#each listItems as |item id|}}
<li class="item flexrow draggable" data-entry-compendium="{{item.compendium}}" data-entry-id="{{id}}">
<div class="item-image">
<img
class=""
data-src="{{item.img}}"
data-tooltip="{{item.name}}"
data-tooltip-direction="UP"
width="32"
height="32"
/>
</div>
<div class="item-name">
<span class="item-edit"
><a data-tooltip="({{item.compendium}})" data-tooltip-direction="UP">{{item.name}}</a></span
>
</div>
<div class="item-tags">
<span data-tooltip="Item Type" data-tooltip-direction="UP">{{item.type}}</span>
</div>
<div class="filter-tags">
<input type="hidden" name="type" value="{{item.type}}" />
</div>
</li>
{{/each}}

View File

@ -0,0 +1,34 @@
<div class="item-browser browser flexrow">
<div class="control-area">
<div class="filtercontainer" id="tagfilter">
<div class="filter" data-type="text" data-path="name">
<input
class=""
name="textFilter"
type="text"
value=""
data-dtype="String"
placeholder="{{localize
'Name'}}"
/>
</div>
<dl id="sorter">
<dt>{{localize "CMPBrowser.sortBy"}}:</dt>
<dd>
<select name="sortorder">
<option value="true" selected>{{localize "Name"}}</option>
<option value="false">{{localize "DND5E.Type"}}</option>
</select>
</dd>
</dl>
<button id="reset-item-filter">{{localize "CMPBrowser.Filters.ResetFilters"}}</button>
</div>
{{> "modules/compendium-browser/templates/filter-container.html" filters=itemFilters}}
</div>
<div class="list-area flexcol">
<ul id="CBItems">
{{> "modules/compendium-browser/templates/item-browser-list.html" items=items}}
</ul>
<span class="loading" id="CBItemsMessage" style="flex: 0"></span>
</div>
</div>

View File

@ -0,0 +1,15 @@
<!-- <img
class=""
src="icons/sundries/books/book-open-turquoise.webp"
data-tooltip="Loading book"
data-tooltip-direction="UP"
width="32"
height="32"
/> -->
<span class="item-edit">
{{#if doneLoading}} {{localize (concat "CMPBrowser.LOADED.Message." itemType) numLoaded=numLoaded}}
<!-- -->
{{else}} {{localize "CMPBrowser.LOADING.Message" numLoaded=numLoaded itemType=itemType}} {{/if}}
<!-- -->
{{#if maxLoaded}}{{localize "CMPBrowser.LOADED.MaxLoaded"}}{{/if}}
</span>

View File

@ -0,0 +1,30 @@
{{#each listItems as |npc id|}}
<li class="npc flexrow draggable" data-entry-compendium="{{npc.compendium}}" data-entry-id="{{id}}">
<div class="npc-image">
<img
class=""
data-src="{{npc.img}}"
data-tooltip="{{npc.name}}"
data-tooltip-direction="UP"
width="32"
height="32"
/>
</div>
<div class="npc-line">
<div class="npc-name">
<span class="item-edit"
><a data-tooltip="({{npc.compendium}})" data-tooltip-direction="UP">{{npc.name}}</a></span
>
</div>
<div class="npc-tags">
<span class="cr" data-tooltip="Challange Rating" data-tooltip-direction="UP">CR {{npc.displayCR}}</span>
<span class="size">{{npc.displaySize}}</span>
<span class="type">{{npc.displayType}}</span>
</div>
<div class="filter-tags">
<input type="hidden" name="order.cr" value="{{npc.orderCR}}" />
<input type="hidden" name="order.size" value="{{npc.orderSize}}" />
</div>
</div>
</li>
{{/each}}

View File

@ -0,0 +1,35 @@
<div class="npc-browser browser flexrow">
<div class="control-area">
<div class="filtercontainer" id="tagfilter">
<div class="filter" data-type="text" data-path="name">
<input
class=""
name="textFilter"
type="text"
value=""
data-dtype="String"
placeholder="{{localize
'Name'}}"
/>
</div>
<dl id="sorter">
<dt>{{localize "CMPBrowser.sortBy"}}:</dt>
<dd>
<select name="sortorder">
<option value="name" selected>{{localize "Name"}}</option>
<option value="cr">{{localize "DND5E.ChallengeRating"}}</option>
<option value="size">{{localize "DND5E.Size"}}</option>
</select>
</dd>
</dl>
<button id="reset-npc-filter">{{localize "CMPBrowser.Filters.ResetFilters"}}</button>
</div>
{{> "modules/compendium-browser/templates/filter-container.html" filters=npcFilters}}
</div>
<div class="list-area flexcol">
<ul id="CBNPCs">
{{> "modules/compendium-browser/templates/npc-browser-list.html" npcs=npcs}}
</ul>
<span class="loading" id="CBNpcsMessage" style="flex: 0"></span>
</div>
</div>

View File

@ -0,0 +1,54 @@
<div class="settings">
<div class="settings-group">
<h3>{{localize "CMPBrowser.generalSettings"}}</h3>
<label>
<input data-setting="allow-spell-browser" type="checkbox" {{checked settings.allowSpellBrowser}} />
<h4>{{localize "CMPBrowser.allowSpellAcc"}}</h4>
</label>
<label>
<input data-setting="allow-feat-browser" type="checkbox" {{checked settings.allowFeatBrowser}} />
<h4>{{localize "CMPBrowser.allowFeatAcc"}}</h4>
</label>
<label>
<input data-setting="allow-item-browser" type="checkbox" {{checked settings.allowItemBrowser}} />
<h4>{{localize "CMPBrowser.allowItemAcc"}}</h4>
</label>
<label>
<input data-setting="allow-npc-browser" type="checkbox" {{checked settings.allowNpcBrowser}} />
<h4>{{localize "CMPBrowser.allowNpcAcc"}}</h4>
</label>
</div>
<div class="settings-group">
<h3>{{localize "CMPBrowser.compSettingsSpell"}}</h3>
{{#each settings.loadedSpellCompendium as |spellComp key|}}
<label>
<input
data-setting="spell-compendium-setting"
data-key="{{key}}"
data-type="spell"
type="checkbox"
{{checked
spellComp.load}}
/>
<h4>{{localize "CMPBrowser.load"}} {{spellComp.name}}</h4>
</label>
{{/each}}
</div>
<div class="settings-group">
<h3>{{localize "CMPBrowser.compSettingsNpc"}}</h3>
{{#each settings.loadedNpcCompendium as |npcComp key|}}
<label>
<input
data-setting="npc-compendium-setting"
data-key="{{key}}"
data-type="npc"
type="checkbox"
{{checked
npcComp.load}}
/>
<h4>{{localize "CMPBrowser.load"}} {{npcComp.name}}</h4>
</label>
{{/each}}
</div>
</div>

View File

@ -0,0 +1,59 @@
{{#each listItems as |spell id|}}
<li class="spell flexrow draggable" data-entry-compendium="{{spell.compendium}}" data-entry-id="{{id}}">
<div class="item-image">
<img
class=""
data-src="{{spell.img}}"
data-tooltip="{{spell.name}}"
data-tooltip-direction="UP"
width="32"
height="32"
/>
</div>
<div class="item-name">
<span class="item-edit"
><a data-tooltip="({{spell.compendium}})" data-tooltip-direction="UP">{{spell.name}}</a></span
>
</div>
<div class="spell-tags">
<span data-tooltip="Spell level" data-tooltip-direction="UP"
>{{#if spell.data.level}}{{spell.data.level}}{{else}}C{{/if}}</span
>
<div class="spacer-large"></div>
<span
class="{{#unless spell.data.properties.ritual}}negative{{/unless}}"
data-tooltip="{{localize 'DND5E.Ritual'}}"
data-tooltip-direction="UP"
>R</span
>
<span
class="{{#unless spell.data.properties.concentration}}negative{{/unless}}"
data-tooltip="{{localize 'DND5E.Concentration'}}"
data-tooltip-direction="UP"
>C</span
>
<div class="spacer"></div>
<span
class="{{#unless spell.data.properties.vocal}}negative{{/unless}}"
data-tooltip="{{localize 'DND5E.ComponentVerbal'}}"
data-tooltip-direction="UP"
>V</span
>
<span
class="{{#unless spell.data.properties.somatic}}negative{{/unless}}"
data-tooltip="{{localize 'DND5E.ComponentSomatic'}}"
data-tooltip-direction="UP"
>S</span
>
<span
class="{{#unless spell.data.properties.material}}negative{{/unless}}"
data-tooltip="{{localize 'DND5E.ComponentMaterial'}}"
data-tooltip-direction="UP"
>M</span
>
</div>
<div class="filter-tags">
<input type="hidden" name="level" value="{{spell.data.level}}" />
</div>
</li>
{{/each}}

View File

@ -0,0 +1,34 @@
<div class="spell-browser browser flexrow">
<div class="control-area">
<div class="filtercontainer" id="tagfilter">
<div class="filter" data-type="text" data-path="name">
<input
class=""
name="textFilter"
type="text"
value=""
data-dtype="String"
placeholder="{{localize
'Name'}}"
/>
</div>
<dl id="sorter">
<dt>{{localize "CMPBrowser.sortBy"}}:</dt>
<dd>
<select name="sortorder">
<option value="true" selected>{{localize "Name"}}</option>
<option value="false">{{localize "DND5E.Level"}}</option>
</select>
</dd>
</dl>
<button id="reset-spell-filter">{{localize "CMPBrowser.Filters.ResetFilters"}}</button>
</div>
{{> "modules/compendium-browser/templates/filter-container.html" filters=spellFilters}}
</div>
<div class="list-area flexcol">
<ul id="CBSpells">
{{> "modules/compendium-browser/templates/spell-browser-list.html" spells=items}}
</ul>
<span class="loading" id="CBSpellsMessage" style="flex: 0"></span>
</div>
</div>

View File

@ -0,0 +1,38 @@
<div class="parent">
<div class="tabs">
{{#if showSpellBrowser}}<a class="item" data-tab="spell"
>{{localize "CMPBrowser.Tab.SpellBrowser"}}</a
>{{/if}} {{#if showFeatBrowser}}<a class="item" data-tab="feat"
>{{localize "CMPBrowser.Tab.FeatBrowser"}}</a
>{{/if}} {{#if showItemBrowser}}<a class="item" data-tab="item"
>{{localize "CMPBrowser.Tab.ItemBrowser"}}</a
>{{/if}} {{#if showNpcBrowser}}<a class="item" data-tab="npc"
>{{localize "CMPBrowser.Tab.NPCBrowser"}}</a
>{{/if}} {{#if isGM}}<a class="item" data-tab="setting"
>{{localize "CMPBrowser.Tab.Settings"}}</a
>{{/if}}
</div>
<div class="content">
<div class="tab" data-tab="spell">
{{#if showSpellBrowser}}{{>
"modules/compendium-browser/templates/spell-browser.html"}}{{/if}}
</div>
<div class="tab" data-tab="feat">
{{#if showFeatBrowser}}{{>
"modules/compendium-browser/templates/feat-browser.html"}}{{/if}}
</div>
<div class="tab" data-tab="item">
{{#if showItemBrowser}}{{>
"modules/compendium-browser/templates/item-browser.html"}}{{/if}}
</div>
<div class="tab" data-tab="npc">
{{#if showNpcBrowser}} {{>
"modules/compendium-browser/templates/npc-browser.html"}}{{/if}}
</div>
<div class="tab" data-tab="setting">
{{#if isGM}} {{>
"modules/compendium-browser/templates/settings.html"}}{{/if}}
</div>
</div>
</div>

View File

@ -1,78 +0,0 @@
{{#each filters.registeredFilterCategorys as |cat key|}}
<div class="filtercontainer" id="{{key}}">
<h3>{{cat.label}}</h3>
<div class="filters">
{{#each cat.filters as |filter key|}}
<div class="filter" data-path="{{filter.path}}" data-type="{{filter.type}}" data-valIsArray="{{filter.valIsArray}}">
{{#if filter.istext}}
<dt>{{filter.label}}</dt>
<dd>
{{#if filter.possibleValues}}
<select class="null">
<option value="" selected>-</option>
{{#each filter.possibleValues as |label val|}}
<option value="{{val}}">{{label}}</option>
{{/each}}
</select>
{{else}}
<input type="text">
{{/if}}
</dd>
{{/if}}
{{#if filter.isbool}}
<dl>
<dt>{{filter.label}}</dt>
<dd>
<select class="null">
<option value="null" selected>-</option>
<option value="true">{{localize "Yes"}}</option>
<option value="false">{{localize "No"}}</option>
</select>
</dd>
</dl>
{{/if}}
{{#if filter.isselect}}
<dl>
<dt>{{filter.label}}</dt>
<dd>
<select class="null">
<option value="null" selected>-</option>
{{#each filter.possibleValues as |label val|}}
<option value="{{val}}">{{label}}</option>
{{/each}}
</select>
</dd>
</dl>
{{/if}}
{{#if filter.ismultiSelect}}
<div class="multiselect">
<label>{{filter.label}}</label>
<dl>
{{#each filter.possibleValues as |label val|}}
<dt><label>{{label}}</label></dt>
<dd><input type="checkbox" data-value="{{val}}"></dd>
{{/each}}
</dl>
</div>
{{/if}}
{{#if filter.isnumberCompare}}
<div class="numberCompare">
<dt>{{filter.label}}</dt>
<dd>
<select class="small-select">
<option value="null" selected>-</option>
<option value="=">=</option>
<option value="<">&lt;</option>
<option value=">">&gt;</option>
</select>
<input class="small-input" type="number">
</dd>
</div>
{{/if}}
</div>
{{/each}}
</div>
</div>
{{/each}}

View File

@ -1,43 +0,0 @@
<div class="npc-browser browser flexrow">
<div class="control-area">
<div class="filtercontainer" id="tagfilter">
<div class="filter" data-type="text" data-path="name">
<input class="" name="textFilter" type="text" value="" data-dtype="String" placeholder="{{localize "Name"}}"/>
</div>
<dl id="sorter">
<dt>{{localize "CMPBrowser.sortBy"}}:</dt>
<dd><select name="sortorder">
<option value="name" selected>{{localize "Name"}}</option>
<option value="cr">{{localize "CMPBrowser.cr"}}</option>
<option value="size">{{localize "DND5E.Size"}}</option>
</select></dd>
</dl>
<button id="reset-npc-filter">Reset NPC Filters</button>
</div>
{{> "modules/compendium-browser/template/filter-container.html" filters=npcFilters}}
</div>
<ul>
{{#each npcs as |npc id|}}
<li class="npc flexrow draggable" data-entry-compendium="{{npc.compendium}}" data-entry-id="{{npc._id}}">
<div class="npc-image">
<img class="" src="{{npc.img}}" title="{{npc.name}}" width="32" height="32" />
</div>
<div class="npc-line">
<div class="npc-name">
<span class="item-edit"><a>{{npc.name}}</a></span>
</div>
<div class="npc-tags">
<span class="cr-display" title="Challange Rating">CR {{npc.displayCR}}</span>
<span class="size-display">{{npc.displaySize}}</span>
<span class="type">{{npc.data.details.type.value}}</span>
</div>
<div class="filter-tags">
<input type="hidden" name="order.cr" value="{{npc.data.details.cr}}">
<input type="hidden" name="order.size" value="{{npc.filterSize}}">
</div>
</div>
</li>
{{/each}}
</ul>
</div>

View File

@ -1,32 +0,0 @@
<div class="settings">
<div class="settings-group">
<h3>{{localize "CMPBrowser.generalSettings"}}</h3>
<label>
<input data-setting="allow-spell-browser" type="checkbox" {{#if settings.allowSpellBrowser}}checked{{/if}}>
<h4>{{localize "CMPBrowser.allowSpellAcc"}}</h4>
</label>
<label>
<input data-setting="allow-npc-browser" type="checkbox" {{#if settings.allowNpcBrowser}}checked{{/if}}>
<h4>{{localize "CMPBrowser.allowNpcAcc"}}</h4>
</label>
</div>
<div class="settings-group">
<h3>{{localize "CMPBrowser.compSettingsSpell"}}</h3>
{{#each settings.loadedSpellCompendium as |spellComp key|}}
<label>
<input data-setting="spell-compendium-setting" data-key="{{key}}" data-type="spell" type="checkbox"{{#if spellComp.load}}checked{{/if}}>
<h4>{{localize "CMPBrowser.load"}} {{spellComp.name}}</h4>
</label>
{{/each}}
</div>
<div class="settings-group">
<h3>{{localize "CMPBrowser.compSettingsNpc"}}</h3>
{{#each settings.loadedNpcCompendium as |npcComp key|}}
<label>
<input data-setting="npc-compendium-setting" data-key="{{key}}" data-type="npc" type="checkbox"{{#if npcComp.load}}checked{{/if}}>
<h4>{{localize "CMPBrowser.load"}} {{npcComp.name}}</h4>
</label>
{{/each}}
</div>
</div>

View File

@ -1,44 +0,0 @@
<div class="spell-browser browser flexrow">
<div class="control-area">
<div class="filtercontainer" id="tagfilter">
<div class="filter" data-type="text" data-path="name">
<input class="" name="textFilter" type="text" value="" data-dtype="String" placeholder="{{localize "Name"}}"/>
</div>
<dl id="sorter">
<dt>{{localize "CMPBrowser.sortBy"}}:</dt>
<dd><select class="null" name="sortorder">
<option value="true" selected>{{localize "Name"}}</option>
<option value="false">{{localize "CMPBrowser.lvl"}}</option>
</select></dd>
</dl>
<button id="reset-spell-filter">Reset Spell Filters</button>
</div>
{{> "modules/compendium-browser/template/filter-container.html" filters=spellFilters}}
</div>
<ul>
{{#each spells as |spell id|}}
<li class="spell flexrow draggable" data-entry-compendium="{{spell.compendium}}" data-entry-id="{{spell._id}}">
<div class="spell-image">
<img class="" src="{{spell.img}}" title="{{spell.name}}" width="32" height="32"/>
</div>
<div class="spell-name">
<span class="item-edit" ><a>{{spell.name}}</a></span>
</div>
<div class="spell-tags">
<span title="Spell level">{{#if spell.data.level}}{{spell.data.level}}{{else}}C{{/if}}</span>
<div class="spacer-large"></div>
<span {{#unless spell.data.components.ritual}}style="color:#bbb;" title="{{localize "No"}} {{localize "CMPBrowser.ritual"}}"{{else}} title="{{localize "CMPBrowser.ritual"}}"{{/unless}}>R</span>
<span {{#unless spell.data.components.concentration}}style="color:#bbb;" title="{{localize "No"}} {{localize "CMPBrowser.concentration"}}"{{else}} title="{{localize "CMPBrowser.concentration"}}"{{/unless}}>C</span>
<div class="spacer"></div>
<span {{#unless spell.data.components.vocal}}style="color:#bbb;" title="{{localize "No"}} {{localize "CMPBrowser.verbal"}}"{{else}} title="{{localize "CMPBrowser.verbal"}}"{{/unless}}>V</span>
<span {{#unless spell.data.components.somatic}}style="color:#bbb;" title="{{localize "No"}} {{localize "CMPBrowser.somatic"}}"{{else}} title="{{localize "CMPBrowser.somatic"}}"{{/unless}}>S</span>
<span {{#unless spell.data.components.material}}style="color:#bbb;" title="no{{localize "No"}} {{localize "CMPBrowser.material"}}"{{else}} title="{{localize "CMPBrowser.material"}}"{{/unless}}>M</span>
</div>
<div class="filter-tags">
<input type="hidden" name="level" value="{{spell.data.level}}">
</div>
</li>
{{/each}}
</ul>
</div>

View File

@ -1,13 +0,0 @@
<div>
<div class="tabs">
{{#if showSpellBrowser}}<a class="item" data-tab="spell">{{localize "CMPBrowser.spellBrowser"}}</a>{{/if}}
{{#if showNpcBrowser}}<a class="item" data-tab="npc">{{localize "CMPBrowser.npcBrowser"}}</a>{{/if}}
{{#if isGM}}<a class="item" data-tab="setting">{{localize "CMPBrowser.settings"}}</a>{{/if}}
</div>
<div class="content">
<div class="tab" data-tab="spell">{{#if showSpellBrowser}}{{> "modules/compendium-browser/template/spell-browser.html"}}{{/if}}</div>
<div class="tab" data-tab="npc">{{#if showNpcBrowser}} {{> "modules/compendium-browser/template/npc-browser.html"}}{{/if}}</div>
<div class="tab" data-tab="setting">{{#if isGM}} {{> "modules/compendium-browser/template/settings.html"}}{{/if}}</div>
</div>
</div>