Skip to content

Instantly share code, notes, and snippets.

@internetimagery
Last active October 14, 2025 08:58
Show Gist options
  • Save internetimagery/0b70030fd098a0ee2491146975cfb05e to your computer and use it in GitHub Desktop.
Save internetimagery/0b70030fd098a0ee2491146975cfb05e to your computer and use it in GitHub Desktop.
Collect tokens for the backs of exported creature cards
# Make cards out of exported lists
# https://5e.tools/makecards.html
# Export then pass to tool to add background images
import json
import argparse
import unicodedata
import urllib.parse
import urllib.request
def translate_source(source: str) -> str:
if source == "MM'25":
return "XMM"
if source == "MM'14":
return "MM"
return source
def get_token_url(creature: dict) -> str:
source = translate_source(creature["tags"][1])
sanitized_title = unicodedata.normalize(
"NFKD",
creature["title"].replace('"', "")
).encode("ascii", "ignore")
name = urllib.parse.quote(sanitized_title)
template = f"https://5e.tools/img/bestiary/tokens/{source}/{name}.webp"
return template
def main(source: str, target: str) -> None:
print("Reading", source)
with open(source, "r") as read:
creatures = json.load(read)
for creature in creatures:
url = get_token_url(creature)
print("Checking", url, end=" ")
code = urllib.request.urlopen(url).getcode()
if code != 200:
print("Failed, Skipped")
continue
print("OK")
creature["background_image"] = url
print("Writing", target)
with open(target, "w") as write:
json.dump(creatures, write, indent=2)
if __name__ == "__main__":
parser = argparse.ArgumentParser()
parser.add_argument("source")
parser.add_argument("target")
args = parser.parse_args()
main(args.source, args.target)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment