23 Commits

Author SHA1 Message Date
4ef1b429f2 version bump 2026-01-07 14:36:21 +01:00
b8314c0e3d don't leave progressbar 2026-01-07 08:15:56 +01:00
60f3ca1f20 reduced thumbnail quality 2025-12-11 08:59:40 +01:00
bc519ac5d0 Remove duplicate 'Star History' section
Removed duplicate 'Star History' section from README.
2025-12-10 13:30:26 +01:00
b0c1b2ce48 Add Star History section to README 2025-12-10 13:29:56 +01:00
faa283efa3 tags optional 2025-11-25 07:07:47 +01:00
ce70aa7bd9 changed python version 2025-11-07 09:22:47 +01:00
59c7cfd406 breaking change: new requirement ConfigArgParse 2025-11-07 09:04:17 +01:00
cfe1585c39 added exception to log 2025-10-27 15:05:10 +01:00
57b6b56388 fixed TypeError 2025-10-27 12:06:14 +01:00
2c6f8fbcb7 move thumbdir declare 2025-10-27 11:12:03 +01:00
30eb1ed8df added metadata dataclass 2025-10-27 09:51:00 +01:00
0ef6e1ccf6 default [] 2025-10-27 06:49:55 +01:00
f24a24bcd2 fixed extension exclude 2025-10-22 14:53:07 +02:00
d1bf0fbc9a added --ignore-extension argument 2025-10-17 15:11:54 +02:00
285227dea7 updated themes 2025-10-10 09:32:31 +02:00
3867d56896 added submodule 2025-10-10 09:26:38 +02:00
d86da24963 moved themes to submodule 2025-10-10 09:25:29 +02:00
922b56c27e update default theme 2025-10-01 10:07:32 +02:00
a67968d222 fixed tag render in title 2025-09-29 17:33:56 +02:00
d094cd6683 test show tags in title 2025-09-29 15:14:17 +02:00
83a29bf62b fixed centering 2025-09-28 17:45:15 +02:00
0f955993ca added title 2025-09-28 16:40:06 +02:00
65 changed files with 462 additions and 3507 deletions

View File

@@ -8,7 +8,7 @@ jobs:
- uses: actions/checkout@v4
- uses: actions/setup-python@v5
with:
python-version: '3.x'
python-version: '3.12'
- name: Install Dependencies
run: pip install -r requirements.txt
- name: Build Package

3
.gitmodules vendored Normal file
View File

@@ -0,0 +1,3 @@
[submodule "themes"]
path = themes
url = https://github.com/greflm13/SGBthemes

View File

@@ -1 +1 @@
2.8.5
2.9.0

View File

@@ -103,3 +103,7 @@ To generate a web manifest file:
## License
This project is licensed under the AGPL-3.0 License. See the [LICENSE](LICENSE) file for details.
## Star History
[![Star History Chart](https://api.star-history.com/svg?repos=greflm13/StaticGalleryBuilder&type=date&legend=top-left)](https://www.star-history.com/#greflm13/StaticGalleryBuilder&type=date&legend=top-left)

View File

@@ -37,8 +37,8 @@ NOT_LIST = ["*/Galleries/*", "Archives"]
args = parse_arguments(VERSION)
lock_file = os.path.join(args.root_directory, ".lock")
if os.path.exists(lock_file):
LOCKFILE = os.path.join(args.root_directory, ".lock")
if os.path.exists(LOCKFILE):
print("Another instance of this program is running.")
sys.exit()
else:
@@ -155,7 +155,7 @@ def generate_thumbnail(arguments: tuple[str, str, str]) -> None:
imgrgb = imgfile.convert("RGB")
img = ImageOps.exif_transpose(imgrgb)
img.thumbnail((512, 512))
img.save(path, "JPEG", quality=75, optimize=True, mode="RGB")
img.save(path, "JPEG", quality=50, optimize=True, mode="RGB", subsampling=2)
except OSError:
logger.error("Failed to generate thumbnail for %s", item, extra={"path": image})
print(f"Failed to generate thumbnail for {image}")
@@ -168,12 +168,13 @@ def main(args) -> None:
"""
Main function to process images and generate a static image hosting website.
"""
thumbnails: list[tuple[str, str, str, bool]] = []
thumbnails: list[tuple[str, str, str]] = []
args, raw = init_globals(args, RAW_EXTENSIONS)
thumbdir = os.path.join(args.root_directory, ".thumbnails")
try:
Path(lock_file).touch()
Path(LOCKFILE).touch()
logger.info("starting builder", extra={"version": VERSION, "arguments": args})
logger.info("getting logo from sorogon.eu")
@@ -195,10 +196,10 @@ def main(args) -> None:
logger.warning("reread metadata flag is set to true, all image metadata will be reread")
if args.regenerate_thumbnails:
logger.warning("regenerate thumbnails flag is set to true, all thumbnails will be regenerated")
if os.path.exists(os.path.join(args.root_directory, ".thumbnails")):
if os.path.exists(thumbdir):
logger.info("removing old thumbnails folder")
shutil.rmtree(os.path.join(args.root_directory, ".thumbnails"))
os.makedirs(os.path.join(args.root_directory, ".thumbnails"), exist_ok=True)
shutil.rmtree(thumbdir)
os.makedirs(thumbdir, exist_ok=True)
copy_static_files(args)
icons(args)
@@ -229,8 +230,11 @@ def main(args) -> None:
dynamic_ncols=True,
):
pass
except Exception as e:
logger.critical("an unhandled exception occurred: %s", str(e), exc_info=True)
print(f"An unhandled exception occurred: {str(e)}")
finally:
os.remove(lock_file)
os.remove(LOCKFILE)
logger.info("finished builder", extra={"version": VERSION})

3
example.config Normal file
View File

@@ -0,0 +1,3 @@
root-directory = /path/to/webroot
site-title = Website Title
web-root-url = https://www.example.com

View File

@@ -277,7 +277,8 @@ a.pswp__share--download:hover {
font-size: 13px;
padding: 10px;
line-height: 20px;
color: #CCC; }
color: #CCC;
text-align: center; }
.pswp__caption--empty {
display: none; }

View File

@@ -1,268 +0,0 @@
import os
import re
import sys
import shutil
import base64
import fileinput
import urllib.parse
import urllib.request
from typing import List
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.chrome.service import Service
from selenium.webdriver.chrome.options import Options
from modules.logger import consolelogger as logger
from modules.css_color import extract_colorscheme
def replace_all(file, search_exp, replace_exp):
for line in fileinput.input(file, inplace=1):
line = re.sub(search_exp, replace_exp, line)
sys.stdout.write(line)
def take_screenshot(html_file_path: str, css_file: str, output_file: str, driver: webdriver.Chrome) -> None:
"""
Takes a screenshot of the given HTML file with the specified CSS applied.
Args:
html_file_path (str): Path to the HTML file or URL.
css_file (str): Path to the CSS file to be applied.
output_file (str): Path where the screenshot will be saved.
driver (webdriver.Chrome): The Chrome WebDriver instance.
"""
logger.info("taking screenshot for %s", css_file)
try:
# Open the HTML file or URL
if html_file_path.startswith(("http://", "https://")):
logger.info("opening URL: %s", html_file_path)
driver.get(html_file_path)
else:
logger.info("opening file: %s", html_file_path)
driver.get(f"file://{os.path.abspath(html_file_path)}")
# Remove current theme.css
remove_css_script = """
var links = document.querySelectorAll("link[rel='stylesheet']");
links.forEach(link => {
if (link.href.includes('theme.css')) {
link.parentNode.removeChild(link);
}
});
"""
logger.info("removing current theme.css")
driver.execute_script(remove_css_script)
with open(css_file, "r", encoding="utf-8") as f:
logger.info("reading CSS file: %s", css_file)
css_content = f.read()
# Extract folder icon content
css_parts = css_content.split(".foldericon {")
css_head = css_parts[0]
css_tail = css_parts[1].split("}", maxsplit=1)[1]
folder_icon_content = css_parts[1].split("}", maxsplit=1)[0].strip()
folder_icon_content = re.sub(r"/\*.*\*/", "", folder_icon_content)
for match in re.finditer(r"content: (.*);", folder_icon_content):
logger.info("found foldericon", extra={"foldericon": folder_icon_content})
folder_icon_content = match.group(1).replace('"', "")
break
if "url" not in folder_icon_content:
logger.info("Reading foldericon svg")
with open(folder_icon_content, "r", encoding="utf-8") as f:
svg = f.read()
if "svg.j2" in folder_icon_content:
logger.info("foldericon in theme file is a jinja2 template")
colorscheme = extract_colorscheme(css_file)
for color_key, color_value in colorscheme.items():
svg = svg.replace(f"{{{{ {color_key} }}}}", color_value)
logger.info("replaced colors in svg")
svg = urllib.parse.quote(svg)
css_content = f'{css_head}\n.foldericon {{\n content: url("data:image/svg+xml,{svg}");\n}}\n{css_tail}'
# Encode CSS content as Base64
logger.info("encoding css content as base64")
encoded_css = base64.b64encode(css_content.encode("utf-8")).decode("utf-8")
# Inject CSS into HTML using JavaScript
apply_css_script = f"""
var style = document.createElement('style');
style.innerHTML = atob('{encoded_css}');
document.head.appendChild(style);
"""
logger.info("injecting CSS into HTML")
driver.execute_script(apply_css_script)
# Wait for a while to ensure CSS is applied
# time.sleep(1)
# Move mouse to info
logger.info("moving mouse to info")
hoverable = driver.find_element(By.CLASS_NAME, "tooltip")
webdriver.ActionChains(driver).move_to_element(hoverable).perform()
# Capture screenshot
logger.info("taking screenshot")
driver.save_screenshot(output_file)
logger.info("screenshot saved to %s", output_file)
except Exception as e:
logger.error("failed to take screenshot for %s: %s", css_file, e)
def create_preview(html_file_path: str, css_file: str, previews_folder: str):
logger.info("creating preview for %s", css_file)
out_file = os.path.basename(css_file).removesuffix(".css") + ".html"
urllib.request.urlretrieve(html_file_path, os.path.join(previews_folder, out_file))
basename = os.path.basename(css_file)
path = css_file.removesuffix(basename)
replace_all(
os.path.join(previews_folder, out_file),
r'^\s*?<link rel="stylesheet" href=".*theme.css">\s*?$',
f' <link rel="stylesheet" href="file://{path}previews/{basename}">',
)
with open(css_file, "r", encoding="utf-8") as f:
theme = f.read()
split = theme.split(".foldericon {")
split2 = split[1].split("}", maxsplit=1)
themehead = split[0]
themetail = split2[1]
foldericon = split2[0].strip()
foldericon = re.sub(r"/\*.*\*/", "", foldericon)
for match in re.finditer(r"content: (.*);", foldericon):
foldericon = match[1]
foldericon = foldericon.replace('"', "")
break
if "url" in foldericon:
logger.info("foldericon in theme file, using it")
shutil.copyfile(css_file, os.path.join(path, "previews", basename))
return
with open(os.path.join(path, foldericon.removeprefix("themes/")), "r", encoding="utf-8") as f:
logger.info("Reading foldericon svg")
svg = f.read()
if "svg.j2" in foldericon:
logger.info("foldericon in theme file is a jinja2 template")
colorscheme = extract_colorscheme(css_file)
for color_key, color_value in colorscheme.items():
svg = svg.replace(f"{{{{ {color_key} }}}}", color_value)
logger.info("replaced colors in svg")
svg = urllib.parse.quote(svg)
if os.path.exists(os.path.join(path, "previews", basename)):
os.remove(os.path.join(path, "previews", basename))
with open(os.path.join(path, "previews", basename), "x", encoding="utf-8") as f:
logger.info("writing theme file")
f.write(themehead + '\n.foldericon {\n content: url("data:image/svg+xml,' + svg + '");\n}\n' + themetail)
logger.info("preview created for %s", css_file)
def write_readme(directory_path: str, themes: List[str]) -> None:
"""
Writes the README file with previews of included themes.
Args:
directory_path (str): Path to the folder containing the themes and README.md.
themes (List[str]): List of theme names.
"""
readme_path = os.path.join(directory_path, "README.md")
try:
with open(readme_path, "r", encoding="utf-8") as f:
logger.info("reading README.md", extra={"file": readme_path})
readme = f.read()
readme_head = readme.split("## Previews of included themes")[0]
readme_head += "## Previews of included themes\n"
readme_head += "".join([f"\n### {theme}\n\n![{theme}](screenshots/{theme}.png)\n" for theme in themes])
with open(readme_path, "w", encoding="utf-8") as f:
logger.info("writing README.md", extra={"file": readme_path})
f.write(readme_head)
logger.info("README.md updated with previews of included themes.")
except FileNotFoundError:
logger.error("README.md not found in %s", directory_path)
except Exception as e:
logger.error("failed to write README.md: %s", e)
def write_index(directory_path: str, themes: List[str]) -> None:
with open(os.path.join(directory_path, "index.html"), "w", encoding="utf-8") as f:
f.write(
"""<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Themes</title>
</head>
<body>"""
)
for theme in themes:
f.write(f'<a href="previews/{theme}.html">{theme}</a><br>\n')
f.write("</body></html>")
def main(directory_path: str, html_file_path: str) -> None:
"""
Main function to take screenshots for each CSS file in the folder and update the README.md.
Args:
directory_path (str): Path to the folder containing CSS files.
html_file_path (str): Path to the HTML file or URL for rendering.
"""
if not os.path.exists(directory_path):
logger.error('Error: Folder path "%s" does not exist.', directory_path)
return
# Setup Chrome options
chrome_options = Options()
chrome_options.add_argument("--headless") # Run in headless mode, no GUI
chrome_options.add_argument("--window-size=1920,1080") # Set window size to at least 1920x1080
# Initialize Chrome WebDriver
chromedriver_path = "/usr/bin/chromedriver"
service = Service(chromedriver_path)
logger.info("Using chromedriver at %s", chromedriver_path, extra={"chrome_options": chrome_options})
driver = webdriver.Chrome(service=service, options=chrome_options)
try:
themes = []
# Iterate over all files in the folder
for filename in sorted(os.listdir(directory_path)):
if filename.endswith(".css"):
theme_name = os.path.splitext(filename)[0]
themes.append(theme_name)
css_file = os.path.join(directory_path, filename)
output_file = os.path.join(directory_path, "screenshots", f"{theme_name}.png")
previews_folder = os.path.join(directory_path, "previews")
# Create screenshots folder if it doesn't exist
os.makedirs(os.path.dirname(output_file), exist_ok=True)
os.makedirs(previews_folder, exist_ok=True)
# Take screenshot for this CSS file
take_screenshot(html_file_path, css_file, output_file, driver)
create_preview(html_file_path, css_file, previews_folder)
# Write the README file with the new previews
write_readme(directory_path, themes)
write_index(directory_path, themes)
finally:
logger.info("closing chrome webdriver")
driver.quit()
if __name__ == "__main__":
if len(sys.argv) != 3:
logger.error("Usage: python script_name.py directory_path html_file_path")
else:
dir_path = sys.argv[1]
html_path = sys.argv[2]
logger.info("Starting script", extra={"directory_path": dir_path, "html_file_path": html_path})
main(dir_path, html_path)
logger.info("Done!", extra={"directory_path": dir_path})

192
help.svg
View File

@@ -1,4 +1,4 @@
<svg class="rich-terminal" viewBox="0 0 1482 928.4" xmlns="http://www.w3.org/2000/svg">
<svg class="rich-terminal" viewBox="0 0 1482 1074.8" xmlns="http://www.w3.org/2000/svg">
<!-- Generated with Rich https://www.textualize.io -->
<style>
@@ -19,183 +19,207 @@
font-weight: 700;
}
.terminal-3378394567-matrix {
.terminal-1915255058-matrix {
font-family: Fira Code, monospace;
font-size: 20px;
line-height: 24.4px;
font-variant-east-asian: full-width;
}
.terminal-3378394567-title {
.terminal-1915255058-title {
font-size: 18px;
font-weight: bold;
font-family: arial;
}
.terminal-3378394567-r1 { fill: #ff8700 }
.terminal-3378394567-r2 { fill: #c5c8c6 }
.terminal-3378394567-r3 { fill: #808080 }
.terminal-3378394567-r4 { fill: #68a0b3 }
.terminal-3378394567-r5 { fill: #00af87 }
.terminal-1915255058-r1 { fill: #ff8700 }
.terminal-1915255058-r2 { fill: #c5c8c6 }
.terminal-1915255058-r3 { fill: #808080 }
.terminal-1915255058-r4 { fill: #68a0b3 }
.terminal-1915255058-r5 { fill: #00af87 }
</style>
<defs>
<clipPath id="terminal-3378394567-clip-terminal">
<rect x="0" y="0" width="1463.0" height="877.4" />
<clipPath id="terminal-1915255058-clip-terminal">
<rect x="0" y="0" width="1463.0" height="1023.8" />
</clipPath>
<clipPath id="terminal-3378394567-line-0">
<clipPath id="terminal-1915255058-line-0">
<rect x="0" y="1.5" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-1">
<clipPath id="terminal-1915255058-line-1">
<rect x="0" y="25.9" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-2">
<clipPath id="terminal-1915255058-line-2">
<rect x="0" y="50.3" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-3">
<clipPath id="terminal-1915255058-line-3">
<rect x="0" y="74.7" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-4">
<clipPath id="terminal-1915255058-line-4">
<rect x="0" y="99.1" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-5">
<clipPath id="terminal-1915255058-line-5">
<rect x="0" y="123.5" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-6">
<clipPath id="terminal-1915255058-line-6">
<rect x="0" y="147.9" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-7">
<clipPath id="terminal-1915255058-line-7">
<rect x="0" y="172.3" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-8">
<clipPath id="terminal-1915255058-line-8">
<rect x="0" y="196.7" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-9">
<clipPath id="terminal-1915255058-line-9">
<rect x="0" y="221.1" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-10">
<clipPath id="terminal-1915255058-line-10">
<rect x="0" y="245.5" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-11">
<clipPath id="terminal-1915255058-line-11">
<rect x="0" y="269.9" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-12">
<clipPath id="terminal-1915255058-line-12">
<rect x="0" y="294.3" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-13">
<clipPath id="terminal-1915255058-line-13">
<rect x="0" y="318.7" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-14">
<clipPath id="terminal-1915255058-line-14">
<rect x="0" y="343.1" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-15">
<clipPath id="terminal-1915255058-line-15">
<rect x="0" y="367.5" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-16">
<clipPath id="terminal-1915255058-line-16">
<rect x="0" y="391.9" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-17">
<clipPath id="terminal-1915255058-line-17">
<rect x="0" y="416.3" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-18">
<clipPath id="terminal-1915255058-line-18">
<rect x="0" y="440.7" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-19">
<clipPath id="terminal-1915255058-line-19">
<rect x="0" y="465.1" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-20">
<clipPath id="terminal-1915255058-line-20">
<rect x="0" y="489.5" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-21">
<clipPath id="terminal-1915255058-line-21">
<rect x="0" y="513.9" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-22">
<clipPath id="terminal-1915255058-line-22">
<rect x="0" y="538.3" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-23">
<clipPath id="terminal-1915255058-line-23">
<rect x="0" y="562.7" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-24">
<clipPath id="terminal-1915255058-line-24">
<rect x="0" y="587.1" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-25">
<clipPath id="terminal-1915255058-line-25">
<rect x="0" y="611.5" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-26">
<clipPath id="terminal-1915255058-line-26">
<rect x="0" y="635.9" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-27">
<clipPath id="terminal-1915255058-line-27">
<rect x="0" y="660.3" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-28">
<clipPath id="terminal-1915255058-line-28">
<rect x="0" y="684.7" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-29">
<clipPath id="terminal-1915255058-line-29">
<rect x="0" y="709.1" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-30">
<clipPath id="terminal-1915255058-line-30">
<rect x="0" y="733.5" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-31">
<clipPath id="terminal-1915255058-line-31">
<rect x="0" y="757.9" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-32">
<clipPath id="terminal-1915255058-line-32">
<rect x="0" y="782.3" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-33">
<clipPath id="terminal-1915255058-line-33">
<rect x="0" y="806.7" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-3378394567-line-34">
<clipPath id="terminal-1915255058-line-34">
<rect x="0" y="831.1" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-1915255058-line-35">
<rect x="0" y="855.5" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-1915255058-line-36">
<rect x="0" y="879.9" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-1915255058-line-37">
<rect x="0" y="904.3" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-1915255058-line-38">
<rect x="0" y="928.7" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-1915255058-line-39">
<rect x="0" y="953.1" width="1464" height="24.65"/>
</clipPath>
<clipPath id="terminal-1915255058-line-40">
<rect x="0" y="977.5" width="1464" height="24.65"/>
</clipPath>
</defs>
<rect fill="#292929" stroke="rgba(255,255,255,0.35)" stroke-width="1" x="1" y="1" width="1480" height="926.4" rx="8"/>
<rect fill="#292929" stroke="rgba(255,255,255,0.35)" stroke-width="1" x="1" y="1" width="1480" height="1072.8" rx="8"/>
<g transform="translate(26,22)">
<circle cx="0" cy="0" r="7" fill="#ff5f57"/>
<circle cx="22" cy="0" r="7" fill="#febc2e"/>
<circle cx="44" cy="0" r="7" fill="#28c840"/>
</g>
<g transform="translate(9, 41)" clip-path="url(#terminal-3378394567-clip-terminal)">
<g transform="translate(9, 41)" clip-path="url(#terminal-1915255058-clip-terminal)">
<g class="terminal-3378394567-matrix">
<text class="terminal-3378394567-r1" x="0" y="20" textLength="73.2" clip-path="url(#terminal-3378394567-line-0)">Usage:</text><text class="terminal-3378394567-r3" x="85.4" y="20" textLength="122" clip-path="url(#terminal-3378394567-line-0)">builder.py</text><text class="terminal-3378394567-r2" x="207.4" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">&#160;[</text><text class="terminal-3378394567-r4" x="231.8" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-h</text><text class="terminal-3378394567-r2" x="256.2" y="20" textLength="36.6" clip-path="url(#terminal-3378394567-line-0)">]&#160;[</text><text class="terminal-3378394567-r4" x="292.8" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-a</text><text class="terminal-3378394567-r5" x="329.4" y="20" textLength="73.2" clip-path="url(#terminal-3378394567-line-0)">AUTHOR</text><text class="terminal-3378394567-r2" x="402.6" y="20" textLength="36.6" clip-path="url(#terminal-3378394567-line-0)">]&#160;[</text><text class="terminal-3378394567-r4" x="439.2" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-e</text><text class="terminal-3378394567-r5" x="475.8" y="20" textLength="109.8" clip-path="url(#terminal-3378394567-line-0)">EXTENSION</text><text class="terminal-3378394567-r2" x="585.6" y="20" textLength="36.6" clip-path="url(#terminal-3378394567-line-0)">]&#160;[</text><text class="terminal-3378394567-r4" x="622.2" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-l</text><text class="terminal-3378394567-r5" x="658.8" y="20" textLength="85.4" clip-path="url(#terminal-3378394567-line-0)">LICENSE</text><text class="terminal-3378394567-r2" x="744.2" y="20" textLength="36.6" clip-path="url(#terminal-3378394567-line-0)">]&#160;[</text><text class="terminal-3378394567-r4" x="780.8" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-m</text><text class="terminal-3378394567-r2" x="805.2" y="20" textLength="36.6" clip-path="url(#terminal-3378394567-line-0)">]&#160;[</text><text class="terminal-3378394567-r4" x="841.8" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-n</text><text class="terminal-3378394567-r2" x="866.2" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">]&#160;</text><text class="terminal-3378394567-r4" x="890.6" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-p</text><text class="terminal-3378394567-r5" x="927.2" y="20" textLength="48.8" clip-path="url(#terminal-3378394567-line-0)">ROOT</text><text class="terminal-3378394567-r4" x="988.2" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-t</text><text class="terminal-3378394567-r5" x="1024.8" y="20" textLength="61" clip-path="url(#terminal-3378394567-line-0)">TITLE</text><text class="terminal-3378394567-r4" x="1098" y="20" textLength="24.4" clip-path="url(#terminal-3378394567-line-0)">-w</text><text class="terminal-3378394567-r5" x="1134.6" y="20" textLength="36.6" clip-path="url(#terminal-3378394567-line-0)">URL</text><text class="terminal-3378394567-r2" x="1464" y="20" textLength="12.2" clip-path="url(#terminal-3378394567-line-0)">
</text><text class="terminal-3378394567-r2" x="0" y="44.4" textLength="231.8" clip-path="url(#terminal-3378394567-line-1)">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;[</text><text class="terminal-3378394567-r4" x="231.8" y="44.4" textLength="195.2" clip-path="url(#terminal-3378394567-line-1)">--exclude-folder</text><text class="terminal-3378394567-r5" x="439.2" y="44.4" textLength="73.2" clip-path="url(#terminal-3378394567-line-1)">FOLDER</text><text class="terminal-3378394567-r2" x="512.4" y="44.4" textLength="36.6" clip-path="url(#terminal-3378394567-line-1)">]&#160;[</text><text class="terminal-3378394567-r4" x="549" y="44.4" textLength="219.6" clip-path="url(#terminal-3378394567-line-1)">--folderthumbnails</text><text class="terminal-3378394567-r2" x="768.6" y="44.4" textLength="36.6" clip-path="url(#terminal-3378394567-line-1)">]&#160;[</text><text class="terminal-3378394567-r4" x="805.2" y="44.4" textLength="244" clip-path="url(#terminal-3378394567-line-1)">--ignore-other-files</text><text class="terminal-3378394567-r2" x="1049.2" y="44.4" textLength="36.6" clip-path="url(#terminal-3378394567-line-1)">]&#160;[</text><text class="terminal-3378394567-r4" x="1085.8" y="44.4" textLength="280.6" clip-path="url(#terminal-3378394567-line-1)">--regenerate-thumbnails</text><text class="terminal-3378394567-r2" x="1366.4" y="44.4" textLength="12.2" clip-path="url(#terminal-3378394567-line-1)">]</text><text class="terminal-3378394567-r2" x="1464" y="44.4" textLength="12.2" clip-path="url(#terminal-3378394567-line-1)">
</text><text class="terminal-3378394567-r2" x="0" y="68.8" textLength="231.8" clip-path="url(#terminal-3378394567-line-2)">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;[</text><text class="terminal-3378394567-r4" x="231.8" y="68.8" textLength="207.4" clip-path="url(#terminal-3378394567-line-2)">--reread-metadata</text><text class="terminal-3378394567-r2" x="439.2" y="68.8" textLength="36.6" clip-path="url(#terminal-3378394567-line-2)">]&#160;[</text><text class="terminal-3378394567-r4" x="475.8" y="68.8" textLength="195.2" clip-path="url(#terminal-3378394567-line-2)">--reread-sidecar</text><text class="terminal-3378394567-r2" x="671" y="68.8" textLength="36.6" clip-path="url(#terminal-3378394567-line-2)">]&#160;[</text><text class="terminal-3378394567-r4" x="707.6" y="68.8" textLength="170.8" clip-path="url(#terminal-3378394567-line-2)">--reverse-sort</text><text class="terminal-3378394567-r2" x="878.4" y="68.8" textLength="36.6" clip-path="url(#terminal-3378394567-line-2)">]&#160;[</text><text class="terminal-3378394567-r4" x="915" y="68.8" textLength="146.4" clip-path="url(#terminal-3378394567-line-2)">--theme-path</text><text class="terminal-3378394567-r5" x="1073.6" y="68.8" textLength="48.8" clip-path="url(#terminal-3378394567-line-2)">PATH</text><text class="terminal-3378394567-r2" x="1122.4" y="68.8" textLength="36.6" clip-path="url(#terminal-3378394567-line-2)">]&#160;[</text><text class="terminal-3378394567-r4" x="1159" y="68.8" textLength="231.8" clip-path="url(#terminal-3378394567-line-2)">--use-fancy-folders</text><text class="terminal-3378394567-r2" x="1390.8" y="68.8" textLength="12.2" clip-path="url(#terminal-3378394567-line-2)">]</text><text class="terminal-3378394567-r2" x="1464" y="68.8" textLength="12.2" clip-path="url(#terminal-3378394567-line-2)">
</text><text class="terminal-3378394567-r2" x="0" y="93.2" textLength="231.8" clip-path="url(#terminal-3378394567-line-3)">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;[</text><text class="terminal-3378394567-r4" x="231.8" y="93.2" textLength="109.8" clip-path="url(#terminal-3378394567-line-3)">--version</text><text class="terminal-3378394567-r2" x="341.6" y="93.2" textLength="12.2" clip-path="url(#terminal-3378394567-line-3)">]</text><text class="terminal-3378394567-r2" x="1464" y="93.2" textLength="12.2" clip-path="url(#terminal-3378394567-line-3)">
</text><text class="terminal-3378394567-r2" x="1464" y="117.6" textLength="12.2" clip-path="url(#terminal-3378394567-line-4)">
</text><text class="terminal-3378394567-r2" x="0" y="142" textLength="658.8" clip-path="url(#terminal-3378394567-line-5)">generate&#160;HTML&#160;files&#160;for&#160;a&#160;static&#160;image&#160;hosting&#160;website</text><text class="terminal-3378394567-r2" x="1464" y="142" textLength="12.2" clip-path="url(#terminal-3378394567-line-5)">
</text><text class="terminal-3378394567-r2" x="1464" y="166.4" textLength="12.2" clip-path="url(#terminal-3378394567-line-6)">
</text><text class="terminal-3378394567-r1" x="0" y="190.8" textLength="97.6" clip-path="url(#terminal-3378394567-line-7)">Options:</text><text class="terminal-3378394567-r2" x="1464" y="190.8" textLength="12.2" clip-path="url(#terminal-3378394567-line-7)">
</text><text class="terminal-3378394567-r4" x="24.4" y="215.2" textLength="24.4" clip-path="url(#terminal-3378394567-line-8)">-h</text><text class="terminal-3378394567-r2" x="48.8" y="215.2" textLength="24.4" clip-path="url(#terminal-3378394567-line-8)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="215.2" textLength="73.2" clip-path="url(#terminal-3378394567-line-8)">--help</text><text class="terminal-3378394567-r2" x="292.8" y="215.2" textLength="378.2" clip-path="url(#terminal-3378394567-line-8)">show&#160;this&#160;help&#160;message&#160;and&#160;exit</text><text class="terminal-3378394567-r2" x="1464" y="215.2" textLength="12.2" clip-path="url(#terminal-3378394567-line-8)">
</text><text class="terminal-3378394567-r4" x="24.4" y="239.6" textLength="24.4" clip-path="url(#terminal-3378394567-line-9)">-a</text><text class="terminal-3378394567-r2" x="48.8" y="239.6" textLength="24.4" clip-path="url(#terminal-3378394567-line-9)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="239.6" textLength="158.6" clip-path="url(#terminal-3378394567-line-9)">--author-name</text><text class="terminal-3378394567-r5" x="244" y="239.6" textLength="73.2" clip-path="url(#terminal-3378394567-line-9)">AUTHOR</text><text class="terminal-3378394567-r2" x="1464" y="239.6" textLength="12.2" clip-path="url(#terminal-3378394567-line-9)">
</text><text class="terminal-3378394567-r2" x="292.8" y="264" textLength="390.4" clip-path="url(#terminal-3378394567-line-10)">name&#160;of&#160;the&#160;author&#160;of&#160;the&#160;images</text><text class="terminal-3378394567-r2" x="1464" y="264" textLength="12.2" clip-path="url(#terminal-3378394567-line-10)">
</text><text class="terminal-3378394567-r4" x="24.4" y="288.4" textLength="24.4" clip-path="url(#terminal-3378394567-line-11)">-e</text><text class="terminal-3378394567-r2" x="48.8" y="288.4" textLength="24.4" clip-path="url(#terminal-3378394567-line-11)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="288.4" textLength="207.4" clip-path="url(#terminal-3378394567-line-11)">--file-extensions</text><text class="terminal-3378394567-r5" x="292.8" y="288.4" textLength="109.8" clip-path="url(#terminal-3378394567-line-11)">EXTENSION</text><text class="terminal-3378394567-r2" x="1464" y="288.4" textLength="12.2" clip-path="url(#terminal-3378394567-line-11)">
</text><text class="terminal-3378394567-r2" x="292.8" y="312.8" textLength="732" clip-path="url(#terminal-3378394567-line-12)">file&#160;extensions&#160;to&#160;include&#160;(can&#160;be&#160;specified&#160;multiple&#160;times)</text><text class="terminal-3378394567-r2" x="1464" y="312.8" textLength="12.2" clip-path="url(#terminal-3378394567-line-12)">
</text><text class="terminal-3378394567-r4" x="24.4" y="337.2" textLength="24.4" clip-path="url(#terminal-3378394567-line-13)">-l</text><text class="terminal-3378394567-r2" x="48.8" y="337.2" textLength="24.4" clip-path="url(#terminal-3378394567-line-13)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="337.2" textLength="170.8" clip-path="url(#terminal-3378394567-line-13)">--license-type</text><text class="terminal-3378394567-r5" x="256.2" y="337.2" textLength="85.4" clip-path="url(#terminal-3378394567-line-13)">LICENSE</text><text class="terminal-3378394567-r2" x="1464" y="337.2" textLength="12.2" clip-path="url(#terminal-3378394567-line-13)">
</text><text class="terminal-3378394567-r2" x="292.8" y="361.6" textLength="475.8" clip-path="url(#terminal-3378394567-line-14)">specify&#160;the&#160;license&#160;type&#160;for&#160;the&#160;images</text><text class="terminal-3378394567-r2" x="1464" y="361.6" textLength="12.2" clip-path="url(#terminal-3378394567-line-14)">
</text><text class="terminal-3378394567-r4" x="24.4" y="386" textLength="24.4" clip-path="url(#terminal-3378394567-line-15)">-m</text><text class="terminal-3378394567-r2" x="48.8" y="386" textLength="24.4" clip-path="url(#terminal-3378394567-line-15)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="386" textLength="170.8" clip-path="url(#terminal-3378394567-line-15)">--web-manifest</text><text class="terminal-3378394567-r2" x="292.8" y="386" textLength="341.6" clip-path="url(#terminal-3378394567-line-15)">generate&#160;a&#160;web&#160;manifest&#160;file</text><text class="terminal-3378394567-r2" x="1464" y="386" textLength="12.2" clip-path="url(#terminal-3378394567-line-15)">
</text><text class="terminal-3378394567-r4" x="24.4" y="410.4" textLength="24.4" clip-path="url(#terminal-3378394567-line-16)">-n</text><text class="terminal-3378394567-r2" x="48.8" y="410.4" textLength="24.4" clip-path="url(#terminal-3378394567-line-16)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="410.4" textLength="268.4" clip-path="url(#terminal-3378394567-line-16)">--non-interactive-mode</text><text class="terminal-3378394567-r2" x="1464" y="410.4" textLength="12.2" clip-path="url(#terminal-3378394567-line-16)">
</text><text class="terminal-3378394567-r2" x="292.8" y="434.8" textLength="634.4" clip-path="url(#terminal-3378394567-line-17)">run&#160;in&#160;non-interactive&#160;mode,&#160;disabling&#160;progress&#160;bars</text><text class="terminal-3378394567-r2" x="1464" y="434.8" textLength="12.2" clip-path="url(#terminal-3378394567-line-17)">
</text><text class="terminal-3378394567-r4" x="24.4" y="459.2" textLength="24.4" clip-path="url(#terminal-3378394567-line-18)">-p</text><text class="terminal-3378394567-r2" x="48.8" y="459.2" textLength="24.4" clip-path="url(#terminal-3378394567-line-18)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="459.2" textLength="195.2" clip-path="url(#terminal-3378394567-line-18)">--root-directory</text><text class="terminal-3378394567-r5" x="280.6" y="459.2" textLength="48.8" clip-path="url(#terminal-3378394567-line-18)">ROOT</text><text class="terminal-3378394567-r2" x="1464" y="459.2" textLength="12.2" clip-path="url(#terminal-3378394567-line-18)">
</text><text class="terminal-3378394567-r2" x="292.8" y="483.6" textLength="439.2" clip-path="url(#terminal-3378394567-line-19)">root&#160;directory&#160;containing&#160;the&#160;images</text><text class="terminal-3378394567-r2" x="1464" y="483.6" textLength="12.2" clip-path="url(#terminal-3378394567-line-19)">
</text><text class="terminal-3378394567-r4" x="24.4" y="508" textLength="24.4" clip-path="url(#terminal-3378394567-line-20)">-t</text><text class="terminal-3378394567-r2" x="48.8" y="508" textLength="24.4" clip-path="url(#terminal-3378394567-line-20)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="508" textLength="146.4" clip-path="url(#terminal-3378394567-line-20)">--site-title</text><text class="terminal-3378394567-r5" x="231.8" y="508" textLength="61" clip-path="url(#terminal-3378394567-line-20)">TITLE</text><text class="terminal-3378394567-r2" x="1464" y="508" textLength="12.2" clip-path="url(#terminal-3378394567-line-20)">
</text><text class="terminal-3378394567-r2" x="292.8" y="532.4" textLength="378.2" clip-path="url(#terminal-3378394567-line-21)">title&#160;of&#160;the&#160;image&#160;hosting&#160;site</text><text class="terminal-3378394567-r2" x="1464" y="532.4" textLength="12.2" clip-path="url(#terminal-3378394567-line-21)">
</text><text class="terminal-3378394567-r4" x="24.4" y="556.8" textLength="24.4" clip-path="url(#terminal-3378394567-line-22)">-w</text><text class="terminal-3378394567-r2" x="48.8" y="556.8" textLength="24.4" clip-path="url(#terminal-3378394567-line-22)">,&#160;</text><text class="terminal-3378394567-r4" x="73.2" y="556.8" textLength="170.8" clip-path="url(#terminal-3378394567-line-22)">--web-root-url</text><text class="terminal-3378394567-r5" x="256.2" y="556.8" textLength="36.6" clip-path="url(#terminal-3378394567-line-22)">URL</text><text class="terminal-3378394567-r2" x="1464" y="556.8" textLength="12.2" clip-path="url(#terminal-3378394567-line-22)">
</text><text class="terminal-3378394567-r2" x="292.8" y="581.2" textLength="622.2" clip-path="url(#terminal-3378394567-line-23)">base&#160;URL&#160;of&#160;the&#160;web&#160;root&#160;for&#160;the&#160;image&#160;hosting&#160;site</text><text class="terminal-3378394567-r2" x="1464" y="581.2" textLength="12.2" clip-path="url(#terminal-3378394567-line-23)">
</text><text class="terminal-3378394567-r4" x="24.4" y="605.6" textLength="195.2" clip-path="url(#terminal-3378394567-line-24)">--exclude-folder</text><text class="terminal-3378394567-r5" x="231.8" y="605.6" textLength="73.2" clip-path="url(#terminal-3378394567-line-24)">FOLDER</text><text class="terminal-3378394567-r2" x="1464" y="605.6" textLength="12.2" clip-path="url(#terminal-3378394567-line-24)">
</text><text class="terminal-3378394567-r2" x="292.8" y="630" textLength="1037" clip-path="url(#terminal-3378394567-line-25)">folders&#160;to&#160;exclude&#160;from&#160;processing,&#160;globs&#160;supported&#160;(can&#160;be&#160;specified&#160;multiple&#160;times)</text><text class="terminal-3378394567-r2" x="1464" y="630" textLength="12.2" clip-path="url(#terminal-3378394567-line-25)">
</text><text class="terminal-3378394567-r4" x="24.4" y="654.4" textLength="219.6" clip-path="url(#terminal-3378394567-line-26)">--folderthumbnails</text><text class="terminal-3378394567-r2" x="292.8" y="654.4" textLength="817.4" clip-path="url(#terminal-3378394567-line-26)">generate&#160;subfolder&#160;thumbnails&#160;(first&#160;image&#160;in&#160;folder&#160;will&#160;be&#160;shown)</text><text class="terminal-3378394567-r2" x="1464" y="654.4" textLength="12.2" clip-path="url(#terminal-3378394567-line-26)">
</text><text class="terminal-3378394567-r4" x="24.4" y="678.8" textLength="244" clip-path="url(#terminal-3378394567-line-27)">--ignore-other-files</text><text class="terminal-3378394567-r2" x="292.8" y="678.8" textLength="671" clip-path="url(#terminal-3378394567-line-27)">ignore&#160;files&#160;that&#160;do&#160;not&#160;match&#160;the&#160;specified&#160;extensions</text><text class="terminal-3378394567-r2" x="1464" y="678.8" textLength="12.2" clip-path="url(#terminal-3378394567-line-27)">
</text><text class="terminal-3378394567-r4" x="24.4" y="703.2" textLength="280.6" clip-path="url(#terminal-3378394567-line-28)">--regenerate-thumbnails</text><text class="terminal-3378394567-r2" x="1464" y="703.2" textLength="12.2" clip-path="url(#terminal-3378394567-line-28)">
</text><text class="terminal-3378394567-r2" x="292.8" y="727.6" textLength="585.6" clip-path="url(#terminal-3378394567-line-29)">regenerate&#160;thumbnails&#160;even&#160;if&#160;they&#160;already&#160;exist</text><text class="terminal-3378394567-r2" x="1464" y="727.6" textLength="12.2" clip-path="url(#terminal-3378394567-line-29)">
</text><text class="terminal-3378394567-r4" x="24.4" y="752" textLength="207.4" clip-path="url(#terminal-3378394567-line-30)">--reread-metadata</text><text class="terminal-3378394567-r2" x="292.8" y="752" textLength="256.2" clip-path="url(#terminal-3378394567-line-30)">reread&#160;image&#160;metadata</text><text class="terminal-3378394567-r2" x="1464" y="752" textLength="12.2" clip-path="url(#terminal-3378394567-line-30)">
</text><text class="terminal-3378394567-r4" x="24.4" y="776.4" textLength="195.2" clip-path="url(#terminal-3378394567-line-31)">--reread-sidecar</text><text class="terminal-3378394567-r2" x="292.8" y="776.4" textLength="244" clip-path="url(#terminal-3378394567-line-31)">reread&#160;sidecar&#160;files</text><text class="terminal-3378394567-r2" x="1464" y="776.4" textLength="12.2" clip-path="url(#terminal-3378394567-line-31)">
</text><text class="terminal-3378394567-r4" x="24.4" y="800.8" textLength="170.8" clip-path="url(#terminal-3378394567-line-32)">--reverse-sort</text><text class="terminal-3378394567-r2" x="292.8" y="800.8" textLength="341.6" clip-path="url(#terminal-3378394567-line-32)">sort&#160;images&#160;in&#160;reverse&#160;order</text><text class="terminal-3378394567-r2" x="1464" y="800.8" textLength="12.2" clip-path="url(#terminal-3378394567-line-32)">
</text><text class="terminal-3378394567-r4" x="24.4" y="825.2" textLength="146.4" clip-path="url(#terminal-3378394567-line-33)">--theme-path</text><text class="terminal-3378394567-r5" x="183" y="825.2" textLength="48.8" clip-path="url(#terminal-3378394567-line-33)">PATH</text><text class="terminal-3378394567-r2" x="292.8" y="825.2" textLength="317.2" clip-path="url(#terminal-3378394567-line-33)">path&#160;to&#160;the&#160;CSS&#160;theme&#160;file</text><text class="terminal-3378394567-r2" x="1464" y="825.2" textLength="12.2" clip-path="url(#terminal-3378394567-line-33)">
</text><text class="terminal-3378394567-r4" x="24.4" y="849.6" textLength="231.8" clip-path="url(#terminal-3378394567-line-34)">--use-fancy-folders</text><text class="terminal-3378394567-r2" x="292.8" y="849.6" textLength="878.4" clip-path="url(#terminal-3378394567-line-34)">enable&#160;fancy&#160;folder&#160;view&#160;instead&#160;of&#160;the&#160;default&#160;Apache&#160;directory&#160;listing</text><text class="terminal-3378394567-r2" x="1464" y="849.6" textLength="12.2" clip-path="url(#terminal-3378394567-line-34)">
</text><text class="terminal-3378394567-r4" x="24.4" y="874" textLength="109.8" clip-path="url(#terminal-3378394567-line-35)">--version</text><text class="terminal-3378394567-r2" x="292.8" y="874" textLength="463.6" clip-path="url(#terminal-3378394567-line-35)">show&#160;program&#x27;s&#160;version&#160;number&#160;and&#160;exit</text><text class="terminal-3378394567-r2" x="1464" y="874" textLength="12.2" clip-path="url(#terminal-3378394567-line-35)">
<g class="terminal-1915255058-matrix">
<text class="terminal-1915255058-r1" x="0" y="20" textLength="73.2" clip-path="url(#terminal-1915255058-line-0)">Usage:</text><text class="terminal-1915255058-r3" x="85.4" y="20" textLength="122" clip-path="url(#terminal-1915255058-line-0)">builder.py</text><text class="terminal-1915255058-r2" x="207.4" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">&#160;[</text><text class="terminal-1915255058-r4" x="231.8" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-h</text><text class="terminal-1915255058-r2" x="256.2" y="20" textLength="36.6" clip-path="url(#terminal-1915255058-line-0)">]&#160;[</text><text class="terminal-1915255058-r4" x="292.8" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-a</text><text class="terminal-1915255058-r5" x="329.4" y="20" textLength="73.2" clip-path="url(#terminal-1915255058-line-0)">AUTHOR</text><text class="terminal-1915255058-r2" x="402.6" y="20" textLength="36.6" clip-path="url(#terminal-1915255058-line-0)">]&#160;[</text><text class="terminal-1915255058-r4" x="439.2" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-e</text><text class="terminal-1915255058-r5" x="475.8" y="20" textLength="109.8" clip-path="url(#terminal-1915255058-line-0)">EXTENSION</text><text class="terminal-1915255058-r2" x="585.6" y="20" textLength="36.6" clip-path="url(#terminal-1915255058-line-0)">]&#160;[</text><text class="terminal-1915255058-r4" x="622.2" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-l</text><text class="terminal-1915255058-r5" x="658.8" y="20" textLength="85.4" clip-path="url(#terminal-1915255058-line-0)">LICENSE</text><text class="terminal-1915255058-r2" x="744.2" y="20" textLength="36.6" clip-path="url(#terminal-1915255058-line-0)">]&#160;[</text><text class="terminal-1915255058-r4" x="780.8" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-m</text><text class="terminal-1915255058-r2" x="805.2" y="20" textLength="36.6" clip-path="url(#terminal-1915255058-line-0)">]&#160;[</text><text class="terminal-1915255058-r4" x="841.8" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-n</text><text class="terminal-1915255058-r2" x="866.2" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">]&#160;</text><text class="terminal-1915255058-r4" x="890.6" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-p</text><text class="terminal-1915255058-r5" x="927.2" y="20" textLength="48.8" clip-path="url(#terminal-1915255058-line-0)">ROOT</text><text class="terminal-1915255058-r4" x="988.2" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-t</text><text class="terminal-1915255058-r5" x="1024.8" y="20" textLength="61" clip-path="url(#terminal-1915255058-line-0)">TITLE</text><text class="terminal-1915255058-r4" x="1098" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-w</text><text class="terminal-1915255058-r5" x="1134.6" y="20" textLength="36.6" clip-path="url(#terminal-1915255058-line-0)">URL</text><text class="terminal-1915255058-r2" x="1171.2" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">&#160;[</text><text class="terminal-1915255058-r4" x="1195.6" y="20" textLength="24.4" clip-path="url(#terminal-1915255058-line-0)">-c</text><text class="terminal-1915255058-r5" x="1232.2" y="20" textLength="134.2" clip-path="url(#terminal-1915255058-line-0)">CONFIG_FILE</text><text class="terminal-1915255058-r2" x="1366.4" y="20" textLength="12.2" clip-path="url(#terminal-1915255058-line-0)">]</text><text class="terminal-1915255058-r2" x="1464" y="20" textLength="12.2" clip-path="url(#terminal-1915255058-line-0)">
</text><text class="terminal-1915255058-r2" x="0" y="44.4" textLength="231.8" clip-path="url(#terminal-1915255058-line-1)">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;[</text><text class="terminal-1915255058-r4" x="231.8" y="44.4" textLength="195.2" clip-path="url(#terminal-1915255058-line-1)">--exclude-folder</text><text class="terminal-1915255058-r5" x="439.2" y="44.4" textLength="73.2" clip-path="url(#terminal-1915255058-line-1)">FOLDER</text><text class="terminal-1915255058-r2" x="512.4" y="44.4" textLength="36.6" clip-path="url(#terminal-1915255058-line-1)">]&#160;[</text><text class="terminal-1915255058-r4" x="549" y="44.4" textLength="219.6" clip-path="url(#terminal-1915255058-line-1)">--folderthumbnails</text><text class="terminal-1915255058-r2" x="768.6" y="44.4" textLength="36.6" clip-path="url(#terminal-1915255058-line-1)">]&#160;[</text><text class="terminal-1915255058-r4" x="805.2" y="44.4" textLength="244" clip-path="url(#terminal-1915255058-line-1)">--ignore-other-files</text><text class="terminal-1915255058-r2" x="1049.2" y="44.4" textLength="36.6" clip-path="url(#terminal-1915255058-line-1)">]&#160;[</text><text class="terminal-1915255058-r4" x="1085.8" y="44.4" textLength="219.6" clip-path="url(#terminal-1915255058-line-1)">--ignore-extension</text><text class="terminal-1915255058-r5" x="1317.6" y="44.4" textLength="109.8" clip-path="url(#terminal-1915255058-line-1)">EXTENSION</text><text class="terminal-1915255058-r2" x="1427.4" y="44.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-1)">]</text><text class="terminal-1915255058-r2" x="1464" y="44.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-1)">
</text><text class="terminal-1915255058-r2" x="0" y="68.8" textLength="231.8" clip-path="url(#terminal-1915255058-line-2)">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;[</text><text class="terminal-1915255058-r4" x="231.8" y="68.8" textLength="280.6" clip-path="url(#terminal-1915255058-line-2)">--regenerate-thumbnails</text><text class="terminal-1915255058-r2" x="512.4" y="68.8" textLength="36.6" clip-path="url(#terminal-1915255058-line-2)">]&#160;[</text><text class="terminal-1915255058-r4" x="549" y="68.8" textLength="207.4" clip-path="url(#terminal-1915255058-line-2)">--reread-metadata</text><text class="terminal-1915255058-r2" x="756.4" y="68.8" textLength="36.6" clip-path="url(#terminal-1915255058-line-2)">]&#160;[</text><text class="terminal-1915255058-r4" x="793" y="68.8" textLength="195.2" clip-path="url(#terminal-1915255058-line-2)">--reread-sidecar</text><text class="terminal-1915255058-r2" x="988.2" y="68.8" textLength="36.6" clip-path="url(#terminal-1915255058-line-2)">]&#160;[</text><text class="terminal-1915255058-r4" x="1024.8" y="68.8" textLength="170.8" clip-path="url(#terminal-1915255058-line-2)">--reverse-sort</text><text class="terminal-1915255058-r2" x="1195.6" y="68.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-2)">]</text><text class="terminal-1915255058-r2" x="1464" y="68.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-2)">
</text><text class="terminal-1915255058-r2" x="0" y="93.2" textLength="231.8" clip-path="url(#terminal-1915255058-line-3)">&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;&#160;[</text><text class="terminal-1915255058-r4" x="231.8" y="93.2" textLength="146.4" clip-path="url(#terminal-1915255058-line-3)">--theme-path</text><text class="terminal-1915255058-r5" x="390.4" y="93.2" textLength="48.8" clip-path="url(#terminal-1915255058-line-3)">PATH</text><text class="terminal-1915255058-r2" x="439.2" y="93.2" textLength="36.6" clip-path="url(#terminal-1915255058-line-3)">]&#160;[</text><text class="terminal-1915255058-r4" x="475.8" y="93.2" textLength="231.8" clip-path="url(#terminal-1915255058-line-3)">--use-fancy-folders</text><text class="terminal-1915255058-r2" x="707.6" y="93.2" textLength="36.6" clip-path="url(#terminal-1915255058-line-3)">]&#160;[</text><text class="terminal-1915255058-r4" x="744.2" y="93.2" textLength="109.8" clip-path="url(#terminal-1915255058-line-3)">--version</text><text class="terminal-1915255058-r2" x="854" y="93.2" textLength="36.6" clip-path="url(#terminal-1915255058-line-3)">]&#160;[</text><text class="terminal-1915255058-r4" x="890.6" y="93.2" textLength="170.8" clip-path="url(#terminal-1915255058-line-3)">--write-config</text><text class="terminal-1915255058-r5" x="1073.6" y="93.2" textLength="134.2" clip-path="url(#terminal-1915255058-line-3)">CONFIG_FILE</text><text class="terminal-1915255058-r2" x="1207.8" y="93.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-3)">]</text><text class="terminal-1915255058-r2" x="1464" y="93.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-3)">
</text><text class="terminal-1915255058-r2" x="1464" y="117.6" textLength="12.2" clip-path="url(#terminal-1915255058-line-4)">
</text><text class="terminal-1915255058-r2" x="0" y="142" textLength="658.8" clip-path="url(#terminal-1915255058-line-5)">generate&#160;HTML&#160;files&#160;for&#160;a&#160;static&#160;image&#160;hosting&#160;website</text><text class="terminal-1915255058-r2" x="1464" y="142" textLength="12.2" clip-path="url(#terminal-1915255058-line-5)">
</text><text class="terminal-1915255058-r2" x="1464" y="166.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-6)">
</text><text class="terminal-1915255058-r1" x="0" y="190.8" textLength="97.6" clip-path="url(#terminal-1915255058-line-7)">Options:</text><text class="terminal-1915255058-r2" x="1464" y="190.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-7)">
</text><text class="terminal-1915255058-r4" x="24.4" y="215.2" textLength="24.4" clip-path="url(#terminal-1915255058-line-8)">-h</text><text class="terminal-1915255058-r2" x="48.8" y="215.2" textLength="24.4" clip-path="url(#terminal-1915255058-line-8)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="215.2" textLength="73.2" clip-path="url(#terminal-1915255058-line-8)">--help</text><text class="terminal-1915255058-r2" x="292.8" y="215.2" textLength="378.2" clip-path="url(#terminal-1915255058-line-8)">show&#160;this&#160;help&#160;message&#160;and&#160;exit</text><text class="terminal-1915255058-r2" x="1464" y="215.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-8)">
</text><text class="terminal-1915255058-r4" x="24.4" y="239.6" textLength="24.4" clip-path="url(#terminal-1915255058-line-9)">-a</text><text class="terminal-1915255058-r2" x="48.8" y="239.6" textLength="24.4" clip-path="url(#terminal-1915255058-line-9)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="239.6" textLength="158.6" clip-path="url(#terminal-1915255058-line-9)">--author-name</text><text class="terminal-1915255058-r5" x="244" y="239.6" textLength="73.2" clip-path="url(#terminal-1915255058-line-9)">AUTHOR</text><text class="terminal-1915255058-r2" x="1464" y="239.6" textLength="12.2" clip-path="url(#terminal-1915255058-line-9)">
</text><text class="terminal-1915255058-r2" x="292.8" y="264" textLength="390.4" clip-path="url(#terminal-1915255058-line-10)">name&#160;of&#160;the&#160;author&#160;of&#160;the&#160;images</text><text class="terminal-1915255058-r2" x="1464" y="264" textLength="12.2" clip-path="url(#terminal-1915255058-line-10)">
</text><text class="terminal-1915255058-r4" x="24.4" y="288.4" textLength="24.4" clip-path="url(#terminal-1915255058-line-11)">-e</text><text class="terminal-1915255058-r2" x="48.8" y="288.4" textLength="24.4" clip-path="url(#terminal-1915255058-line-11)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="288.4" textLength="207.4" clip-path="url(#terminal-1915255058-line-11)">--file-extensions</text><text class="terminal-1915255058-r5" x="292.8" y="288.4" textLength="109.8" clip-path="url(#terminal-1915255058-line-11)">EXTENSION</text><text class="terminal-1915255058-r2" x="1464" y="288.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-11)">
</text><text class="terminal-1915255058-r2" x="292.8" y="312.8" textLength="732" clip-path="url(#terminal-1915255058-line-12)">file&#160;extensions&#160;to&#160;include&#160;(can&#160;be&#160;specified&#160;multiple&#160;times)</text><text class="terminal-1915255058-r2" x="1464" y="312.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-12)">
</text><text class="terminal-1915255058-r4" x="24.4" y="337.2" textLength="24.4" clip-path="url(#terminal-1915255058-line-13)">-l</text><text class="terminal-1915255058-r2" x="48.8" y="337.2" textLength="24.4" clip-path="url(#terminal-1915255058-line-13)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="337.2" textLength="170.8" clip-path="url(#terminal-1915255058-line-13)">--license-type</text><text class="terminal-1915255058-r5" x="256.2" y="337.2" textLength="85.4" clip-path="url(#terminal-1915255058-line-13)">LICENSE</text><text class="terminal-1915255058-r2" x="1464" y="337.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-13)">
</text><text class="terminal-1915255058-r2" x="292.8" y="361.6" textLength="475.8" clip-path="url(#terminal-1915255058-line-14)">specify&#160;the&#160;license&#160;type&#160;for&#160;the&#160;images</text><text class="terminal-1915255058-r2" x="1464" y="361.6" textLength="12.2" clip-path="url(#terminal-1915255058-line-14)">
</text><text class="terminal-1915255058-r4" x="24.4" y="386" textLength="24.4" clip-path="url(#terminal-1915255058-line-15)">-m</text><text class="terminal-1915255058-r2" x="48.8" y="386" textLength="24.4" clip-path="url(#terminal-1915255058-line-15)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="386" textLength="170.8" clip-path="url(#terminal-1915255058-line-15)">--web-manifest</text><text class="terminal-1915255058-r2" x="292.8" y="386" textLength="341.6" clip-path="url(#terminal-1915255058-line-15)">generate&#160;a&#160;web&#160;manifest&#160;file</text><text class="terminal-1915255058-r2" x="1464" y="386" textLength="12.2" clip-path="url(#terminal-1915255058-line-15)">
</text><text class="terminal-1915255058-r4" x="24.4" y="410.4" textLength="24.4" clip-path="url(#terminal-1915255058-line-16)">-n</text><text class="terminal-1915255058-r2" x="48.8" y="410.4" textLength="24.4" clip-path="url(#terminal-1915255058-line-16)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="410.4" textLength="268.4" clip-path="url(#terminal-1915255058-line-16)">--non-interactive-mode</text><text class="terminal-1915255058-r2" x="1464" y="410.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-16)">
</text><text class="terminal-1915255058-r2" x="292.8" y="434.8" textLength="634.4" clip-path="url(#terminal-1915255058-line-17)">run&#160;in&#160;non-interactive&#160;mode,&#160;disabling&#160;progress&#160;bars</text><text class="terminal-1915255058-r2" x="1464" y="434.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-17)">
</text><text class="terminal-1915255058-r4" x="24.4" y="459.2" textLength="24.4" clip-path="url(#terminal-1915255058-line-18)">-p</text><text class="terminal-1915255058-r2" x="48.8" y="459.2" textLength="24.4" clip-path="url(#terminal-1915255058-line-18)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="459.2" textLength="195.2" clip-path="url(#terminal-1915255058-line-18)">--root-directory</text><text class="terminal-1915255058-r5" x="280.6" y="459.2" textLength="48.8" clip-path="url(#terminal-1915255058-line-18)">ROOT</text><text class="terminal-1915255058-r2" x="1464" y="459.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-18)">
</text><text class="terminal-1915255058-r2" x="292.8" y="483.6" textLength="439.2" clip-path="url(#terminal-1915255058-line-19)">root&#160;directory&#160;containing&#160;the&#160;images</text><text class="terminal-1915255058-r2" x="1464" y="483.6" textLength="12.2" clip-path="url(#terminal-1915255058-line-19)">
</text><text class="terminal-1915255058-r4" x="24.4" y="508" textLength="24.4" clip-path="url(#terminal-1915255058-line-20)">-t</text><text class="terminal-1915255058-r2" x="48.8" y="508" textLength="24.4" clip-path="url(#terminal-1915255058-line-20)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="508" textLength="146.4" clip-path="url(#terminal-1915255058-line-20)">--site-title</text><text class="terminal-1915255058-r5" x="231.8" y="508" textLength="61" clip-path="url(#terminal-1915255058-line-20)">TITLE</text><text class="terminal-1915255058-r2" x="1464" y="508" textLength="12.2" clip-path="url(#terminal-1915255058-line-20)">
</text><text class="terminal-1915255058-r2" x="292.8" y="532.4" textLength="378.2" clip-path="url(#terminal-1915255058-line-21)">title&#160;of&#160;the&#160;image&#160;hosting&#160;site</text><text class="terminal-1915255058-r2" x="1464" y="532.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-21)">
</text><text class="terminal-1915255058-r4" x="24.4" y="556.8" textLength="24.4" clip-path="url(#terminal-1915255058-line-22)">-w</text><text class="terminal-1915255058-r2" x="48.8" y="556.8" textLength="24.4" clip-path="url(#terminal-1915255058-line-22)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="556.8" textLength="170.8" clip-path="url(#terminal-1915255058-line-22)">--web-root-url</text><text class="terminal-1915255058-r5" x="256.2" y="556.8" textLength="36.6" clip-path="url(#terminal-1915255058-line-22)">URL</text><text class="terminal-1915255058-r2" x="1464" y="556.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-22)">
</text><text class="terminal-1915255058-r2" x="292.8" y="581.2" textLength="622.2" clip-path="url(#terminal-1915255058-line-23)">base&#160;URL&#160;of&#160;the&#160;web&#160;root&#160;for&#160;the&#160;image&#160;hosting&#160;site</text><text class="terminal-1915255058-r2" x="1464" y="581.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-23)">
</text><text class="terminal-1915255058-r4" x="24.4" y="605.6" textLength="24.4" clip-path="url(#terminal-1915255058-line-24)">-c</text><text class="terminal-1915255058-r2" x="48.8" y="605.6" textLength="24.4" clip-path="url(#terminal-1915255058-line-24)">,&#160;</text><text class="terminal-1915255058-r4" x="73.2" y="605.6" textLength="158.6" clip-path="url(#terminal-1915255058-line-24)">--config-file</text><text class="terminal-1915255058-r5" x="244" y="605.6" textLength="134.2" clip-path="url(#terminal-1915255058-line-24)">CONFIG_FILE</text><text class="terminal-1915255058-r2" x="1464" y="605.6" textLength="12.2" clip-path="url(#terminal-1915255058-line-24)">
</text><text class="terminal-1915255058-r2" x="292.8" y="630" textLength="195.2" clip-path="url(#terminal-1915255058-line-25)">config&#160;file&#160;path</text><text class="terminal-1915255058-r2" x="1464" y="630" textLength="12.2" clip-path="url(#terminal-1915255058-line-25)">
</text><text class="terminal-1915255058-r4" x="24.4" y="654.4" textLength="195.2" clip-path="url(#terminal-1915255058-line-26)">--exclude-folder</text><text class="terminal-1915255058-r5" x="231.8" y="654.4" textLength="73.2" clip-path="url(#terminal-1915255058-line-26)">FOLDER</text><text class="terminal-1915255058-r2" x="1464" y="654.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-26)">
</text><text class="terminal-1915255058-r2" x="292.8" y="678.8" textLength="1037" clip-path="url(#terminal-1915255058-line-27)">folders&#160;to&#160;exclude&#160;from&#160;processing,&#160;globs&#160;supported&#160;(can&#160;be&#160;specified&#160;multiple&#160;times)</text><text class="terminal-1915255058-r2" x="1464" y="678.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-27)">
</text><text class="terminal-1915255058-r4" x="24.4" y="703.2" textLength="219.6" clip-path="url(#terminal-1915255058-line-28)">--folderthumbnails</text><text class="terminal-1915255058-r2" x="292.8" y="703.2" textLength="817.4" clip-path="url(#terminal-1915255058-line-28)">generate&#160;subfolder&#160;thumbnails&#160;(first&#160;image&#160;in&#160;folder&#160;will&#160;be&#160;shown)</text><text class="terminal-1915255058-r2" x="1464" y="703.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-28)">
</text><text class="terminal-1915255058-r4" x="24.4" y="727.6" textLength="244" clip-path="url(#terminal-1915255058-line-29)">--ignore-other-files</text><text class="terminal-1915255058-r2" x="292.8" y="727.6" textLength="671" clip-path="url(#terminal-1915255058-line-29)">ignore&#160;files&#160;that&#160;do&#160;not&#160;match&#160;the&#160;specified&#160;extensions</text><text class="terminal-1915255058-r2" x="1464" y="727.6" textLength="12.2" clip-path="url(#terminal-1915255058-line-29)">
</text><text class="terminal-1915255058-r4" x="24.4" y="752" textLength="219.6" clip-path="url(#terminal-1915255058-line-30)">--ignore-extension</text><text class="terminal-1915255058-r5" x="256.2" y="752" textLength="109.8" clip-path="url(#terminal-1915255058-line-30)">EXTENSION</text><text class="terminal-1915255058-r2" x="1464" y="752" textLength="12.2" clip-path="url(#terminal-1915255058-line-30)">
</text><text class="terminal-1915255058-r2" x="292.8" y="776.4" textLength="719.8" clip-path="url(#terminal-1915255058-line-31)">file&#160;extensions&#160;to&#160;ignore&#160;(can&#160;be&#160;specified&#160;multiple&#160;times)</text><text class="terminal-1915255058-r2" x="1464" y="776.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-31)">
</text><text class="terminal-1915255058-r4" x="24.4" y="800.8" textLength="280.6" clip-path="url(#terminal-1915255058-line-32)">--regenerate-thumbnails</text><text class="terminal-1915255058-r2" x="1464" y="800.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-32)">
</text><text class="terminal-1915255058-r2" x="292.8" y="825.2" textLength="585.6" clip-path="url(#terminal-1915255058-line-33)">regenerate&#160;thumbnails&#160;even&#160;if&#160;they&#160;already&#160;exist</text><text class="terminal-1915255058-r2" x="1464" y="825.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-33)">
</text><text class="terminal-1915255058-r4" x="24.4" y="849.6" textLength="207.4" clip-path="url(#terminal-1915255058-line-34)">--reread-metadata</text><text class="terminal-1915255058-r2" x="292.8" y="849.6" textLength="256.2" clip-path="url(#terminal-1915255058-line-34)">reread&#160;image&#160;metadata</text><text class="terminal-1915255058-r2" x="1464" y="849.6" textLength="12.2" clip-path="url(#terminal-1915255058-line-34)">
</text><text class="terminal-1915255058-r4" x="24.4" y="874" textLength="195.2" clip-path="url(#terminal-1915255058-line-35)">--reread-sidecar</text><text class="terminal-1915255058-r2" x="292.8" y="874" textLength="244" clip-path="url(#terminal-1915255058-line-35)">reread&#160;sidecar&#160;files</text><text class="terminal-1915255058-r2" x="1464" y="874" textLength="12.2" clip-path="url(#terminal-1915255058-line-35)">
</text><text class="terminal-1915255058-r4" x="24.4" y="898.4" textLength="170.8" clip-path="url(#terminal-1915255058-line-36)">--reverse-sort</text><text class="terminal-1915255058-r2" x="292.8" y="898.4" textLength="341.6" clip-path="url(#terminal-1915255058-line-36)">sort&#160;images&#160;in&#160;reverse&#160;order</text><text class="terminal-1915255058-r2" x="1464" y="898.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-36)">
</text><text class="terminal-1915255058-r4" x="24.4" y="922.8" textLength="146.4" clip-path="url(#terminal-1915255058-line-37)">--theme-path</text><text class="terminal-1915255058-r5" x="183" y="922.8" textLength="48.8" clip-path="url(#terminal-1915255058-line-37)">PATH</text><text class="terminal-1915255058-r2" x="292.8" y="922.8" textLength="317.2" clip-path="url(#terminal-1915255058-line-37)">path&#160;to&#160;the&#160;CSS&#160;theme&#160;file</text><text class="terminal-1915255058-r2" x="1464" y="922.8" textLength="12.2" clip-path="url(#terminal-1915255058-line-37)">
</text><text class="terminal-1915255058-r4" x="24.4" y="947.2" textLength="231.8" clip-path="url(#terminal-1915255058-line-38)">--use-fancy-folders</text><text class="terminal-1915255058-r2" x="292.8" y="947.2" textLength="878.4" clip-path="url(#terminal-1915255058-line-38)">enable&#160;fancy&#160;folder&#160;view&#160;instead&#160;of&#160;the&#160;default&#160;Apache&#160;directory&#160;listing</text><text class="terminal-1915255058-r2" x="1464" y="947.2" textLength="12.2" clip-path="url(#terminal-1915255058-line-38)">
</text><text class="terminal-1915255058-r4" x="24.4" y="971.6" textLength="109.8" clip-path="url(#terminal-1915255058-line-39)">--version</text><text class="terminal-1915255058-r2" x="292.8" y="971.6" textLength="463.6" clip-path="url(#terminal-1915255058-line-39)">show&#160;program&#x27;s&#160;version&#160;number&#160;and&#160;exit</text><text class="terminal-1915255058-r2" x="1464" y="971.6" textLength="12.2" clip-path="url(#terminal-1915255058-line-39)">
</text><text class="terminal-1915255058-r4" x="24.4" y="996" textLength="170.8" clip-path="url(#terminal-1915255058-line-40)">--write-config</text><text class="terminal-1915255058-r5" x="207.4" y="996" textLength="134.2" clip-path="url(#terminal-1915255058-line-40)">CONFIG_FILE</text><text class="terminal-1915255058-r2" x="1464" y="996" textLength="12.2" clip-path="url(#terminal-1915255058-line-40)">
</text><text class="terminal-1915255058-r2" x="292.8" y="1020.4" textLength="561.2" clip-path="url(#terminal-1915255058-line-41)">write&#160;current&#160;command&#160;line&#160;args&#160;to&#160;config&#160;file</text><text class="terminal-1915255058-r2" x="1464" y="1020.4" textLength="12.2" clip-path="url(#terminal-1915255058-line-41)">
</text>
</g>
</g>

Before

Width:  |  Height:  |  Size: 28 KiB

After

Width:  |  Height:  |  Size: 32 KiB

View File

@@ -1,7 +1,8 @@
from dataclasses import dataclass
from typing import Optional
import os
import argparse
import configargparse
try:
from rich_argparse import RichHelpFormatter, HelpPreviewAction
@@ -19,6 +20,14 @@ SCRIPTDIR = os.path.abspath(os.path.dirname(__file__).removesuffix(PACKAGE))
DEFAULT_THEME_PATH = os.path.join(SCRIPTDIR, "templates", "default.css")
DEFAULT_AUTHOR = "Author"
if "APPDATA" in os.environ:
CONFIGHOME = os.environ["APPDATA"]
elif "XDG_CONFIG_HOME" in os.environ:
CONFIGHOME = os.environ["XDG_CONFIG_HOME"]
else:
CONFIGHOME = os.path.join(os.environ["HOME"], ".config")
CONFIGPATH = os.path.join(CONFIGHOME, "StaticGalleryBuilder")
@dataclass(init=True)
class Args:
@@ -62,6 +71,7 @@ class Args:
file_extensions: list[str]
folder_thumbs: bool
generate_webmanifest: bool
ignore_extensions: list[str]
ignore_other_files: bool
license_type: Optional[str]
non_interactive_mode: bool
@@ -82,6 +92,7 @@ class Args:
result["file_extensions"] = self.file_extensions
result["folder_thumbs"] = self.folder_thumbs
result["generate_webmanifest"] = self.generate_webmanifest
result["ignore_extensions"] = self.ignore_extensions
result["ignore_other_files"] = self.ignore_other_files
if self.license_type is not None:
result["license_type"] = self.license_type
@@ -114,9 +125,9 @@ def parse_arguments(version: str) -> Args:
"""
# fmt: off
if RICH:
parser = argparse.ArgumentParser(description="generate HTML files for a static image hosting website", formatter_class=RichHelpFormatter)
parser = configargparse.ArgumentParser(default_config_files=[CONFIGPATH], add_config_file_help=False, description="generate HTML files for a static image hosting website", formatter_class=RichHelpFormatter)
else:
parser = argparse.ArgumentParser(description="generate HTML files for a static image hosting website")
parser = configargparse.ArgumentParser(default_config_files=[CONFIGPATH], add_config_file_help=False, description="generate HTML files for a static image hosting website")
parser.add_argument("-a", "--author-name", help="name of the author of the images", default=DEFAULT_AUTHOR, type=str, dest="author_name", metavar="AUTHOR")
parser.add_argument("-e", "--file-extensions", help="file extensions to include (can be specified multiple times)", action="append", dest="file_extensions", metavar="EXTENSION")
parser.add_argument("-l", "--license-type", help="specify the license type for the images", choices=["cc-zero", "cc-by", "cc-by-sa", "cc-by-nd", "cc-by-nc", "cc-by-nc-sa", "cc-by-nc-nd"], default=None, dest="license_type", metavar="LICENSE")
@@ -125,11 +136,13 @@ def parse_arguments(version: str) -> Args:
parser.add_argument("-p", "--root-directory", help="root directory containing the images", required=True, type=str, dest="root_directory", metavar="ROOT")
parser.add_argument("-t", "--site-title", help="title of the image hosting site", required=True, type=str, dest="site_title", metavar="TITLE")
parser.add_argument("-w", "--web-root-url", help="base URL of the web root for the image hosting site", required=True, type=str, dest="web_root_url", metavar="URL")
parser.add_argument('-c', '--config-file', is_config_file=True, help='config file path', metavar="CONFIG_FILE")
parser.add_argument("--exclude-folder", help="folders to exclude from processing, globs supported (can be specified multiple times)", action="append", dest="exclude_folders", metavar="FOLDER")
parser.add_argument("--folderthumbnails", help="generate subfolder thumbnails (first image in folder will be shown)", action="store_true", default=False, dest="folder_thumbs")
if RICH:
parser.add_argument("--generate-help-preview", action=HelpPreviewAction, path="help.svg", )
parser.add_argument("--generate-help-preview", action=HelpPreviewAction, path="help.svg")
parser.add_argument("--ignore-other-files", help="ignore files that do not match the specified extensions", action="store_true", default=False, dest="ignore_other_files")
parser.add_argument("--ignore-extension", help="file extensions to ignore (can be specified multiple times)", action="append", default=[], dest="ignore_extensions", metavar="EXTENSION")
parser.add_argument("--regenerate-thumbnails", help="regenerate thumbnails even if they already exist", action="store_true", default=False, dest="regenerate_thumbnails")
parser.add_argument("--reread-metadata", help="reread image metadata", action="store_true", default=False, dest="reread_metadata")
parser.add_argument("--reread-sidecar", help="reread sidecar files", action="store_true", default=False, dest="reread_sidecar")
@@ -137,7 +150,12 @@ def parse_arguments(version: str) -> Args:
parser.add_argument("--theme-path", help="path to the CSS theme file", default=DEFAULT_THEME_PATH, type=str, dest="theme_path", metavar="PATH")
parser.add_argument("--use-fancy-folders", help="enable fancy folder view instead of the default Apache directory listing", action="store_true", default=False, dest="use_fancy_folders")
parser.add_argument("--version", action="version", version=f"%(prog)s {version}")
parser.add_argument("--write-config", type=str, required=False, help="write current command line args to config file", metavar="CONFIG_FILE")
parsed_args = parser.parse_args()
if parsed_args.write_config:
config_path = parsed_args.write_config
del parsed_args.write_config
parser.write_config_file(parsed_args, [config_path], exit_after=False)
# fmt: on
_args = Args(
author_name=parsed_args.author_name,
@@ -146,6 +164,7 @@ def parse_arguments(version: str) -> Args:
folder_thumbs=parsed_args.folder_thumbs,
generate_webmanifest=parsed_args.generate_webmanifest,
ignore_other_files=parsed_args.ignore_other_files,
ignore_extensions=parsed_args.ignore_extensions,
license_type=parsed_args.license_type,
non_interactive_mode=parsed_args.non_interactive_mode,
regenerate_thumbnails=parsed_args.regenerate_thumbnails,

View File

@@ -95,7 +95,8 @@ def css_color_to_hex(css_color: str) -> str:
# Helper function to convert HSL tuple to RGB tuple
def hsl_to_rgb(hsl: tuple[int, float, float]) -> tuple[int, int, int]:
logger.debug("converting hsl tuple to rgb tuple", extra={"hsl": hsl})
return tuple(round(c * 255) for c in colorsys.hls_to_rgb(hsl[0] / 360, hsl[1] / 100, hsl[2] / 100))
r, g, b = colorsys.hls_to_rgb(hsl[0] / 360, hsl[1] / 100, hsl[2] / 100)
return (round(r * 255), round(g * 255), round(b * 255))
# Regular expression pattern to match CSS colors
color_pattern = re.compile(

View File

@@ -0,0 +1,158 @@
from dataclasses import dataclass
from typing import List, Optional, Any, Dict, TypeVar, Callable, Type, cast
T = TypeVar("T")
def from_int(x: Any) -> int:
assert isinstance(x, int) and not isinstance(x, bool)
return x
def from_str(x: Any) -> str:
assert isinstance(x, str)
return x
def from_list(f: Callable[[Any], T], x: Any) -> List[T]:
assert isinstance(x, list)
return [f(y) for y in x]
def from_none(x: Any) -> Any:
assert x is None
return x
def from_union(fs, x):
for f in fs:
try:
return f(x)
except AssertionError:
pass
assert False
def to_class(c: Type[T], x: Any) -> dict:
assert isinstance(x, c)
return cast(Any, x).to_dict()
def from_dict(f: Callable[[Any], T], x: Any) -> Dict[str, T]:
assert isinstance(x, dict)
return {k: f(v) for (k, v) in x.items()}
def from_native_dict(f: Callable[[Any], T], x: Any) -> Dict[Any, T]:
assert isinstance(x, dict)
return x
@dataclass
class ImageMetadata:
w: Optional[int]
h: Optional[int]
tags: Optional[List[str]]
exifdata: Optional[Dict[str, Any]]
xmp: Optional[Dict[str, Any]]
src: str
msrc: str
name: str
title: str
tiff: Optional[str] = None
raw: Optional[str] = None
@staticmethod
def from_dict(obj: Any) -> "ImageMetadata":
assert isinstance(obj, dict)
w = from_union([from_int, from_none], obj.get("w"))
h = from_union([from_int, from_none], obj.get("h"))
tags = from_union([lambda x: from_list(from_str, x), from_none], obj.get("tags"))
exifdata = from_union([lambda x: from_native_dict(dict, x), from_none], obj.get("exifdata"))
xmp = from_union([lambda x: from_native_dict(dict, x), from_none], obj.get("xmp"))
src = from_str(obj.get("src"))
msrc = from_str(obj.get("msrc"))
name = from_str(obj.get("name"))
title = from_str(obj.get("title"))
tiff = from_union([from_str, from_none], obj.get("tiff"))
raw = from_union([from_str, from_none], obj.get("raw"))
return ImageMetadata(w, h, tags, exifdata, xmp, src, msrc, name, title, tiff, raw)
def to_dict(self) -> dict:
result: dict = {}
if self.w is not None:
result["w"] = from_union([from_int, from_none], self.w)
if self.h is not None:
result["h"] = from_union([from_int, from_none], self.h)
if self.tags is not None:
result["tags"] = from_union([lambda x: from_list(from_str, x), from_none], self.tags)
result["src"] = from_str(self.src)
result["msrc"] = from_str(self.msrc)
result["name"] = from_str(self.name)
result["title"] = from_str(self.title)
if self.tiff is not None:
result["tiff"] = from_union([from_str, from_none], self.tiff)
if self.raw is not None:
result["raw"] = from_union([from_str, from_none], self.raw)
if self.exifdata is not None:
result["exifdata"] = from_union([lambda x: from_native_dict(dict, x), from_none], self.exifdata)
if self.xmp is not None:
result["xmp"] = from_union([lambda x: from_native_dict(dict, x), from_none], self.xmp)
return result
@dataclass
class SubfolderMetadata:
url: str
name: str
metadata: Optional[str] = None
thumb: Optional[str] = None
@staticmethod
def from_dict(obj: Any) -> "SubfolderMetadata":
assert isinstance(obj, dict)
url = from_str(obj.get("url"))
name = from_str(obj.get("name"))
metadata = from_union([from_none, from_str], obj.get("metadata"))
thumb = from_union([from_none, from_str], obj.get("thumb"))
return SubfolderMetadata(url, name, metadata, thumb)
def to_dict(self) -> dict:
result: dict = {}
result["url"] = from_str(self.url)
result["name"] = from_str(self.name)
result["metadata"] = from_union([from_none, from_str], self.metadata)
result["thumb"] = from_union([from_none, from_str], self.thumb)
return result
@dataclass
class Metadata:
images: Dict[str, ImageMetadata]
subfolders: Optional[List[SubfolderMetadata]] = None
@staticmethod
def from_dict(obj: Any) -> "Metadata":
assert isinstance(obj, dict)
images = from_dict(ImageMetadata.from_dict, obj.get("images"))
subfolders = from_union([lambda x: from_list(SubfolderMetadata.from_dict, x), from_none], obj.get("subfolders"))
return Metadata(images, subfolders)
def to_dict(self) -> dict:
result: dict = {}
result["images"] = from_dict(lambda x: to_class(ImageMetadata, x), self.images)
if self.subfolders is not None:
result["subfolders"] = from_union([lambda x: from_list(lambda x: to_class(SubfolderMetadata, x), x), from_none], self.subfolders)
return result
def sort(self, reverse=False) -> "Metadata":
self.images = {key: self.images[key] for key in sorted(self.images, reverse=reverse)}
return self
def top_level_from_dict(s: Any) -> Metadata:
return Metadata.from_dict(s)
def top_level_to_dict(x: Metadata) -> Any:
return to_class(Metadata, x)

View File

@@ -17,6 +17,7 @@ from bs4 import BeautifulSoup
from modules.logger import logger
from modules import cclicense
from modules.argumentparser import Args
from modules.datatypes.metadata import Metadata, ImageMetadata, SubfolderMetadata
# Constants for file paths and exclusions
if __package__ is None:
@@ -73,7 +74,7 @@ def getxmp(strbuffer: str) -> dict[str, Any]:
return {get_name(root.tag): get_value(root)}
def initialize_metadata(folder: str) -> dict[str, dict[str, int]]:
def initialize_metadata(folder: str) -> Metadata:
"""
Initializes the metadata JSON file if it doesn't exist.
@@ -125,11 +126,13 @@ def initialize_metadata(folder: str) -> dict[str, dict[str, int]]:
metadata["images"][k]["exifdata"] = None
if "xmp" not in v:
metadata["images"][k]["xmp"] = None
if "title" not in v:
metadata["images"][k]["title"] = v["name"]
return metadata
return Metadata.from_dict(metadata)
def update_metadata(metadata: dict[str, dict[str, Any]], folder: str) -> None:
def update_metadata(metadata: Metadata, folder: str) -> None:
"""
Updates the metadata JSON file.
@@ -141,14 +144,14 @@ def update_metadata(metadata: dict[str, dict[str, Any]], folder: str) -> None:
if metadata:
with open(metadata_path, "w", encoding="utf-8") as metadatafile:
logger.info("writing metadata file", extra={"file": metadata_path})
metadatafile.write(json.dumps(metadata, indent=4))
metadatafile.write(json.dumps(metadata.to_dict(), indent=4))
else:
if os.path.exists(metadata_path):
logger.info("deleting empty metadata file", extra={"file": metadata_path})
os.remove(metadata_path)
def get_image_info(item: str, folder: str) -> dict[str, Any]:
def get_image_info(item: str, folder: str) -> ImageMetadata:
"""
Extracts image information and EXIF data.
@@ -170,7 +173,7 @@ def get_image_info(item: str, folder: str) -> dict[str, Any]:
except UnidentifiedImageError:
logger.error("cannot identify image file", extra={"file": file})
print(f"cannot identify image file: {file}")
return {"w": None, "h": None, "tags": None, "exifdata": None, "xmp": None}
return ImageMetadata(w=None, h=None, tags=[], exifdata=None, xmp=None, src="", msrc="", name="", title="")
if exif:
logger.info("extracting EXIF data", extra={"file": file})
ifd = exif.get_ifd(ExifTags.IFD.Exif)
@@ -251,9 +254,11 @@ def get_image_info(item: str, folder: str) -> dict[str, Any]:
tags = get_tags(sidecarfile)
except Exception as e:
logger.error(e)
if None in tags:
tags.remove(None)
return {"w": width, "h": height, "tags": tags, "exifdata": exifdata, "xmp": xmp}
if None in tags: # type: ignore
tags.remove(None) # type: ignore
if not isinstance(tags, list):
tags = []
return ImageMetadata(w=width, h=height, tags=tags, exifdata=exifdata, xmp=xmp, src="", msrc="", name="", title="")
def nested_dict():
@@ -329,12 +334,12 @@ def get_tags(sidecarfile: str) -> list[str]:
pass
except KeyError:
pass
if None in tags:
tags.remove(None)
return tags
if None in tags: # type: ignore
tags.remove(None) # type: ignore
return tags # type: ignore
def process_image(item: str, folder: str, _args: Args, baseurl: str, metadata: dict[str, dict[str, int]], raw: list[str]) -> dict[str, Any]:
def process_image(item: str, folder: str, _args: Args, baseurl: str, metadata: Metadata, raw: list[str]) -> tuple[ImageMetadata, Metadata]:
"""
Processes an image and prepares its data for the HTML template.
@@ -351,23 +356,21 @@ def process_image(item: str, folder: str, _args: Args, baseurl: str, metadata: d
"""
extsplit = os.path.splitext(item)
sidecarfile = os.path.join(folder, item + ".xmp")
if item not in metadata["images"] or _args.reread_metadata:
metadata["images"][item] = get_image_info(item, folder)
if item not in metadata.images or _args.reread_metadata:
metadata.images[item] = get_image_info(item, folder)
if _args.reread_sidecar and os.path.exists(sidecarfile):
logger.info("xmp sidecar file found", extra={"file": sidecarfile})
try:
metadata["images"][item]["tags"] = get_tags(sidecarfile)
metadata.images[item].tags = get_tags(sidecarfile)
except Exception as e:
logger.error(e)
image = {
"src": f"{_args.web_root_url}{baseurl}{urllib.parse.quote(item)}",
"msrc": f"{_args.web_root_url}.thumbnails/{baseurl}{urllib.parse.quote(item)}.jpg",
"name": item,
"w": metadata["images"][item]["w"],
"h": metadata["images"][item]["h"],
"tags": metadata["images"][item]["tags"],
}
image = metadata.images[item]
image.src = f"{_args.web_root_url}{baseurl}{urllib.parse.quote(item)}"
image.msrc = f"{_args.web_root_url}.thumbnails/{baseurl}{urllib.parse.quote(item)}.jpg"
image.name = item
image.title = item
path = os.path.join(_args.root_directory, ".thumbnails", baseurl, item + ".jpg")
if not os.path.exists(path) or _args.regenerate_thumbnails:
if os.path.exists(path):
@@ -380,17 +383,17 @@ def process_image(item: str, folder: str, _args: Args, baseurl: str, metadata: d
url = f"{_args.web_root_url}{baseurl}{urllib.parse.quote(extsplit[0])}{_raw}"
if _raw in (".tif", ".tiff"):
logger.info("tiff file found", extra={"file": file})
image["tiff"] = url
image.tiff = url
else:
logger.info("raw file found", extra={"file": file, "extension": _raw})
image["raw"] = url
image.raw = url
metadata["images"][item].update(image)
metadata.images[item] = image
return image, metadata
def generate_html(folder: str, title: str, _args: Args, raw: list[str], version: str, logo: str) -> list[str]:
def generate_html(folder: str, title: str, _args: Args, raw: list[str], version: str, logo: str) -> set[str]:
"""
Generates HTML content for a folder of images.
@@ -409,23 +412,23 @@ def generate_html(folder: str, title: str, _args: Args, raw: list[str], version:
items = sorted(os.listdir(folder))
contains_files = False
images = []
subfolders = []
subfoldertags = set()
images: list[ImageMetadata] = []
subfolders: list[SubfolderMetadata] = []
subfoldertags: set[str] = set()
foldername = folder.removeprefix(_args.root_directory)
foldername = f"{foldername}/" if foldername else ""
baseurl = urllib.parse.quote(foldername)
gone = [item for item in metadata["images"] if item not in items]
gone = [item for item in metadata.images if item not in items]
for gon in gone:
del metadata["images"][gon]
del metadata.images[gon]
create_thumbnail_folder(foldername, _args.root_directory)
logger.info("processing contents", extra={"folder": folder})
if not _args.non_interactive_mode:
for item in tqdm(items, total=len(items), desc=f"Getting image infos - {folder}", unit="files", ascii=True, dynamic_ncols=True):
if item not in EXCLUDES and not item.startswith("."):
for item in tqdm(items, total=len(items), desc=f"Getting image infos - {folder}", unit="files", ascii=True, dynamic_ncols=True, leave=False):
if item not in EXCLUDES and not item.startswith(".") and os.path.splitext(item)[1][1:].lower() not in _args.ignore_extensions:
if os.path.isdir(os.path.join(folder, item)):
subfoldertags.update(process_subfolder(item, folder, baseurl, subfolders, _args, raw, version, logo))
else:
@@ -439,7 +442,7 @@ def generate_html(folder: str, title: str, _args: Args, raw: list[str], version:
process_license(folder, item)
else:
for item in items:
if item not in EXCLUDES and not item.startswith("."):
if item not in EXCLUDES and not item.startswith(".") and os.path.splitext(item)[1][1:].lower() not in _args.ignore_extensions:
if os.path.isdir(os.path.join(folder, item)):
subfoldertags.update(process_subfolder(item, folder, baseurl, subfolders, _args, raw, version, logo))
else:
@@ -452,11 +455,11 @@ def generate_html(folder: str, title: str, _args: Args, raw: list[str], version:
if item == "LICENSE":
process_license(folder, item)
metadata["subfolders"] = subfolders
metadata.subfolders = subfolders
if _args.reverse_sort:
metadata["images"] = {key: metadata["images"][key] for key in sorted(metadata["images"], reverse=True)}
metadata.sort(reverse=True)
else:
metadata["images"] = {key: metadata["images"][key] for key in sorted(metadata["images"])}
metadata.sort()
update_metadata(metadata, folder)
if should_generate_html(images, contains_files, _args):
@@ -482,7 +485,7 @@ def create_thumbnail_folder(foldername: str, root_directory: str) -> None:
os.mkdir(thumbnails_path)
def process_subfolder(item: str, folder: str, baseurl: str, subfolders: list[dict[str, str | None]], _args: Args, raw: list[str], version: str, logo: str) -> list[str]:
def process_subfolder(item: str, folder: str, baseurl: str, subfolders: list[SubfolderMetadata], _args: Args, raw: list[str], version: str, logo: str) -> set[str]:
"""
Processes a subfolder.
@@ -510,10 +513,10 @@ def process_subfolder(item: str, folder: str, baseurl: str, subfolders: list[dic
if item not in _args.exclude_folders:
if not any(fnmatch.fnmatchcase(os.path.join(folder, item), exclude) for exclude in _args.exclude_folders):
subfolders.append({"url": subfolder_url, "name": item, "thumb": thumb, "metadata": f"{_args.web_root_url}{baseurl}{urllib.parse.quote(item)}/.metadata.json"})
subfolders.append(SubfolderMetadata(url=subfolder_url, name=item, thumb=thumb, metadata=f"{_args.web_root_url}{baseurl}{urllib.parse.quote(item)}/.metadata.json"))
return generate_html(os.path.join(folder, item), os.path.join(folder, item).removeprefix(_args.root_directory), _args, raw, version, logo)
subfolders.append({"url": subfolder_url, "name": item, "thumb": thumb, "metadata": None})
return []
subfolders.append(SubfolderMetadata(url=subfolder_url, name=item, thumb=thumb))
return set()
def process_license(folder: str, item: str) -> None:
@@ -545,7 +548,7 @@ def process_info_file(folder: str, item: str) -> None:
info[urllib.parse.quote(folder)] = f.read()
def should_generate_html(images: list[dict[str, Any]], contains_files, _args: Args) -> bool:
def should_generate_html(images: list[ImageMetadata], contains_files, _args: Args) -> bool:
"""
Determines if HTML should be generated.
@@ -556,7 +559,7 @@ def should_generate_html(images: list[dict[str, Any]], contains_files, _args: Ar
Returns:
bool: True if HTML should be generated, False otherwise.
"""
return images or (_args.use_fancy_folders and not contains_files) or (_args.use_fancy_folders and _args.ignore_other_files)
return bool(images) or (_args.use_fancy_folders and not contains_files) or (_args.use_fancy_folders and _args.ignore_other_files)
def format_html(html: str) -> str:
@@ -565,8 +568,8 @@ def format_html(html: str) -> str:
def create_html_file(
folder: str, title: str, foldername: str, images: list[dict[str, Any]], subfolders: list[dict[str, str]], _args: Args, version: str, logo: str, subfoldertags: list[str]
) -> list[str]:
folder: str, title: str, foldername: str, images: list[ImageMetadata], subfolders: list[SubfolderMetadata], _args: Args, version: str, logo: str, subfoldertags: set[str]
) -> set[str]:
"""
Creates the HTML file using the template.
@@ -599,15 +602,13 @@ def create_html_file(
alltags = set()
for img in images:
if img["tags"]:
alltags.update(img["tags"])
if img.tags:
alltags.update(img.tags)
alltags.update(set(subfoldertags))
alltags.update(subfoldertags)
folder_info = info.get(urllib.parse.quote(folder), "").split("\n")
_info = [i for i in folder_info if len(i) > 1] if folder_info else None
if _args.reverse_sort:
images.sort(key=lambda i: i["name"], reverse=True)
folder_license = licens.get(urllib.parse.quote(folder), False)
@@ -658,7 +659,7 @@ def create_html_file(
logger.info("writing formatted html file", extra={"path": html_file})
f.write(format_html(content))
return sorted(alltags)
return set(sorted(alltags))
def list_folder(folder: str, title: str, _args: Args, raw: list[str], version: str, logo: str) -> list[tuple[str, str, str]]:

View File

@@ -1,5 +1,6 @@
beautifulsoup4~=4.13.4
CairoSVG~=2.7.1
ConfigArgParse~=1.7.1
defusedxml~=0.7.1
html5lib~=1.1
Jinja2~=3.1.6

View File

@@ -53,7 +53,7 @@
}
.tagentry label:hover {
background-color: var(--color7);
background-color: var(--color4);
}
.tagentry .tagtoggle:hover {
@@ -74,6 +74,27 @@
font-weight: 800;
}
.loader {
width: 48px;
height: 48px;
border-radius: 50%;
display: inline-block;
border-top: 3px solid var(--bcolor2);
border-right: 3px solid transparent;
box-sizing: border-box;
animation: rotation 1s linear infinite;
}
@keyframes rotation {
0% {
transform: rotate(0deg);
}
100% {
transform: rotate(360deg);
}
}
body {
color: var(--bcolor2);
background-color: var(--bcolor1);

View File

@@ -248,12 +248,76 @@ class PhotoGallery {
}
}
insertPath(obj, path) {
let current = obj;
for (let i = 0; i < path.length; i++) {
const part = path[i];
if (i === path.length - 1) {
if (!current[part]) {
current[part] = null;
}
} else {
if (!current[part] || typeof current[part] !== "object") {
current[part] = {};
}
current = current[part];
}
}
}
finalize(obj) {
if (typeof obj === "object" && obj !== null && !Array.isArray(obj)) {
const result = {};
Object.keys(obj)
.sort()
.forEach((key) => {
if (obj[key] === null) {
result[key] = [];
} else {
result[key] = this.finalize(obj[key]);
}
});
return result;
}
return obj || [];
}
parseHierarchicalTags(tags, delimiter = "|") {
const tree = {};
for (const tag of tags) {
const parts = tag.split(delimiter);
this.insertPath(tree, parts);
}
return this.finalize(tree);
}
renderTree = (obj, depth = 0) => {
let lines = [];
const indent = "&nbsp;&nbsp;".repeat(depth);
for (const key of Object.keys(obj)) {
lines.push(indent + key);
if (Array.isArray(obj[key])) {
for (const val of obj[key]) {
lines.push("&nbsp;&nbsp;".repeat(depth + 1) + val);
}
} else if (typeof obj[key] === "object" && obj[key] !== null) {
lines = lines.concat(this.renderTree(obj[key], depth + 1));
}
}
return lines.join("\n");
};
updateImageList() {
const imagelist = document.getElementById("imagelist");
if (!imagelist) return;
let str = "";
this.shown.forEach((item, index) => {
str += `<div class="column"><figure><img src="${item.msrc}" data-index="${index}" /><figcaption class="caption">${item.name}`;
let tags = this.parseHierarchicalTags(item.tags || []);
str += `<div class="column"><figure title="${this.renderTree(
tags
)}"><img src="${
item.msrc
}" data-index="${index}" /><figcaption class="caption">${item.name}`;
if (item.tiff) str += `&nbsp;<a href="${item.tiff}">TIFF</a>`;
if (item.raw) str += `&nbsp;<a href="${item.raw}">RAW</a>`;
str += "</figcaption></figure></div>";

1
themes Submodule

Submodule themes added at fa79867f4a

View File

@@ -1,106 +0,0 @@
# Custom CSS Themes
You can create custom Themes. They must at least include the following:
## Requirements for Themes
### Required Variables
Define the following variables in your theme:
- `--color1`: Primary color
- `--color2`: Secondary color
- `--color3`: Additional color
- `--color4`: Another color
These variables are essential for automatic icon generation.
### Folder Icon Specification
Include the following CSS rule to specify the folder icon used in your theme:
```css
.foldericon {
content: url("data:image/svg+xml,%3Csvg width='800px' height='800px' viewBox='0 0 1024 1024' class='icon' version='1.1' xmlns='http://www.w3.org/2000/svg' fill='%23000000'%3E%3Cg id='SVGRepo_bgCarrier' stroke-width='0' /%3E%3Cg id='SVGRepo_tracerCarrier' stroke-linecap='round' stroke-linejoin='round' /%3E%3Cg id='SVGRepo_iconCarrier'%3E%3Cpath d='M853.333333 256H469.333333l-85.333333-85.333333H170.666667c-46.933333 0-85.333333 38.4-85.333334 85.333333v170.666667h853.333334v-85.333334c0-46.933333-38.4-85.333333-85.333334-85.333333z' fill='%233674e7' /%3E%3Cpath d='M853.333333 256H170.666667c-46.933333 0-85.333333 38.4-85.333334 85.333333v426.666667c0 46.933333 38.4 85.333333 85.333334 85.333333h682.666666c46.933333 0 85.333333-38.4 85.333334-85.333333V341.333333c0-46.933333-38.4-85.333333-85.333334-85.333333z' fill='%236495ed' /%3E%3C/g%3E%3C/svg%3E");
}
```
Replace the SVG data URI (`url("data:image/svg+xml,...")`) with your desired SVG icon content.
## Previews of included themes
### alpenglow-dark
![alpenglow-dark](screenshots/alpenglow-dark.png)
### alpenglow
![alpenglow](screenshots/alpenglow.png)
### aritim-dark
![aritim-dark](screenshots/aritim-dark.png)
### aritim
![aritim](screenshots/aritim.png)
### autumn
![autumn](screenshots/autumn.png)
### carnation
![carnation](screenshots/carnation.png)
### catpuccin
![catpuccin](screenshots/catpuccin.png)
### cornflower
![cornflower](screenshots/cornflower.png)
### default-dark
![default-dark](screenshots/default-dark.png)
### default
![default](screenshots/default.png)
### ivy
![ivy](screenshots/ivy.png)
### kjoe
![kjoe](screenshots/kjoe.png)
### monokai-vibrant
![monokai-vibrant](screenshots/monokai-vibrant.png)
### rainbow
![rainbow](screenshots/rainbow.png)
### spring
![spring](screenshots/spring.png)
### steam
![steam](screenshots/steam.png)
### summer
![summer](screenshots/summer.png)
### sunflower
![sunflower](screenshots/sunflower.png)
### winter
![winter](screenshots/winter.png)

View File

@@ -1,140 +0,0 @@
@import url("https://fonts.cdnfonts.com/css/metropolis-2");
* {
--color1: #ffa769;
--color2: #fc4ca0;
--color3: #7542e5;
--color4: #ff4ad9;
--color5: #5f2eca;
--color6: #7033ca;
--color7: #ff778e;
--bcolor1: #e2d9f8;
--bcolor2: #20123a;
--bcolor3: #2b1753;
--bcolor4: #321c64;
--gradient: linear-gradient(
80deg,
var(--bcolor2) 0%,
var(--color5) 1%,
var(--color3) 2%,
var(--color2) 3%,
var(--color1) 4%,
var(--color1) 96%,
var(--color2) 97%,
var(--color3) 98%,
var(--color5) 99%,
var(--bcolor2) 100%
);
}
body {
color: var(--bcolor1);
background-color: var(--bcolor3);
font-family: "Metropolis", sans-serif;
font-optical-sizing: auto;
font-weight: 500;
font-style: normal;
}
.navbar {
font-weight: 800;
color: var(--bcolor1);
background-color: var(--color3);
background-image: var(--gradient);
}
.navbar li a {
font-weight: 800;
color: var(--bcolor1);
}
.navbar li a:hover {
text-decoration: none;
background-color: var(--color4);
}
.footer {
color: var(--bcolor2);
background-color: var(--color1);
font-weight: 600;
}
.footer a {
color: var(--color2);
text-decoration: none;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/catpuccin.svg.j2";
}
.folders a {
font-weight: 500;
color: var(--bcolor1);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color7);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 500;
background-color: var(--color6);
}
.tagentry label:hover {
background-color: var(--color3);
}
.tagentry .tagtoggle:hover {
background-color: var(--color3);
}
.column img {
background-color: var(--bcolor2);
}
#totop:hover {
background-color: var(--color6);
}
#totop {
background-color: var(--bcolor4);
color: var(--bcolor1);
font-weight: 600;
}
.loader {
width: 48px;
height: 48px;
border-radius: 50%;
display: inline-block;
border-top: 3px solid var(--bcolor1);
border-right: 3px solid transparent;
box-sizing: border-box;
animation: rotation 1s linear infinite;
}
@keyframes rotation {
0% {
transform: rotate(0deg);
}
100% {
transform: rotate(360deg);
}
}

View File

@@ -1,139 +0,0 @@
@import url("https://fonts.cdnfonts.com/css/metropolis-2");
* {
--color1: #ffa769;
--color2: #fc4ca0;
--color3: #7542e5;
--color4: #ff4ad9;
--color5: #ff778e;
--color6: #fff5f6;
--color7: #5f2eca;
--bcolor1: #ffe7ea;
--bcolor2: #20123b;
--bcolor3: #2b1753;
--bcolor4: #321c64;
--gradient: linear-gradient(80deg,
var(--bcolor2) 0%,
var(--color3) 1%,
var(--color4) 2%,
var(--color5) 3%,
var(--color1) 4%,
var(--color1) 96%,
var(--color5) 97%,
var(--color4) 98%,
var(--color3) 99%,
var(--bcolor2) 100%);
}
body {
color: var(--bcolor2);
background-color: var(--color6);
font-family: "Metropolis", sans-serif;
font-optical-sizing: auto;
font-weight: 500;
font-style: normal;
}
.navbar {
font-weight: 800;
color: var(--bcolor2);
background-color: var(--color5);
background-image: var(--gradient);
}
.navbar li a {
font-weight: 800;
color: var(--bcolor2);
}
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor1);
background-color: var(--bcolor4);
font-weight: 600;
}
.footer a {
color: var(--color5);
text-decoration: none;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/catpuccin.svg.j2";
}
.folders a {
font-weight: 500;
color: var(--bcolor2);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color7);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 500;
color: var(--bcolor1);
background-color: var(--color3);
}
.tagentry label:hover {
background-color: var(--color7);
}
.tagentry .tagtoggle:hover {
background-color: var(--color7);
}
.column img {
background-color: var(--bcolor1);
}
#totop:hover {
background-color: var(--color3);
}
#totop {
background-color: var(--color2);
color: var(--bcolor2);
font-weight: 600;
}
.loader {
width: 48px;
height: 48px;
border-radius: 50%;
display: inline-block;
border-top: 3px solid var(--bcolor2);
border-right: 3px solid transparent;
box-sizing: border-box;
animation: rotation 1s linear infinite;
}
@keyframes rotation {
0% {
transform: rotate(0deg);
}
100% {
transform: rotate(360deg);
}
}

View File

@@ -1,152 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Poppins:wght@300;400;500;600;700&display=swap");
* {
--color1: #5d88ca;
--color2: #27ae60;
--color3: #f67400;
--color4: #da4453;
--color5: #212b36;
--bcolor1: #10151a;
--bcolor2: #d3dae3;
--bcolor3: #141a21;
}
.navbar {
font-weight: 600;
color: var(--bcolor2);
background-color: var(--color5);
}
.navbar li a {
font-weight: 500;
color: var(--bcolor2);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--bcolor3);
}
.footer {
color: var(--bcolor1);
background-color: var(--color2);
font-weight: 500;
}
.footer a {
color: var(--color4);
text-decoration: none;
font-weight: 400;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-papirus.svg.j2";
}
.folders a {
font-weight: 600;
color: var(--bcolor2);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color1);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 400;
background-color: var(--bcolor1);
}
.tagentry label:hover {
background-color: var(--bcolor3);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor3);
}
.column img {
background-color: var(--bcolor1);
}
#totop:hover {
background-color: var(--color3);
}
#totop {
background-color: var(--color5);
color: var(--bcolor2);
font-weight: 600;
}
.loader {
width: 48px;
height: 48px;
border-radius: 50%;
position: relative;
animation: rotate 1s linear infinite
}
.loader::before {
content: "";
box-sizing: border-box;
position: absolute;
inset: 0px;
border-radius: 50%;
border: 5px solid var(--bcolor2);
animation: prixClipFix 2s linear infinite;
}
@keyframes rotate {
100% {
transform: rotate(360deg)
}
}
@keyframes prixClipFix {
0% {
clip-path: polygon(50% 50%, 0 0, 0 0, 0 0, 0 0, 0 0)
}
25% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 0, 100% 0, 100% 0)
}
50% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 100% 100%, 100% 100%)
}
75% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 0 100%, 0 100%)
}
100% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 0 100%, 0 0)
}
}
body {
color: var(--bcolor2);
background-color: var(--bcolor3);
font-family: "Poppins", sans-serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}

View File

@@ -1,152 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Poppins:wght@300;400;500;600;700&display=swap");
* {
--color1: #1d99f3;
--color2: #27ae60;
--color3: #f67400;
--color4: #da4453;
--color5: #eef2f5;
--bcolor1: #a3a5ac;
--bcolor2: #303030;
--bcolor3: #eff0f1;
}
.navbar {
font-weight: 600;
color: var(--bcolor2);
background-color: var(--bcolor1);
}
.navbar li a {
font-weight: 500;
color: var(--bcolor2);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
color: var(--bcolor1);
background-color: var(--bcolor2);
}
.footer {
color: var(--bcolor2);
background-color: var(--color3);
font-weight: 500;
}
.footer a {
color: var(--color4);
text-decoration: none;
font-weight: 400;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-papirus.svg.j2";
}
.folders a {
font-weight: 600;
color: var(--bcolor2);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color1);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 400;
background-color: var(--bcolor1);
}
.tagentry label:hover {
background-color: var(--bcolor3);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor3);
}
.column img {
background-color: var(--bcolor1);
}
#totop:hover {
background-color: var(--color4);
}
#totop {
background-color: var(--color5);
color: var(--bcolor2);
font-weight: 600;
}
.loader {
width: 48px;
height: 48px;
border-radius: 50%;
position: relative;
animation: rotate 1s linear infinite
}
.loader::before {
content: "";
box-sizing: border-box;
position: absolute;
inset: 0px;
border-radius: 50%;
border: 5px solid var(--bcolor2);
animation: prixClipFix 2s linear infinite;
}
@keyframes rotate {
100% {
transform: rotate(360deg)
}
}
@keyframes prixClipFix {
0% {
clip-path: polygon(50% 50%, 0 0, 0 0, 0 0, 0 0, 0 0)
}
25% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 0, 100% 0, 100% 0)
}
50% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 100% 100%, 100% 100%)
}
75% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 0 100%, 0 100%)
}
100% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 0 100%, 0 0)
}
}
body {
color: var(--bcolor2);
background-color: var(--bcolor3);
font-family: "Poppins", sans-serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}

View File

@@ -1,168 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Playfair+Display:wght@400;500;600;700;800;900&display=swap");
* {
--color1: #FF7F50;
/* Coral */
--color2: #D2691E;
/* Chocolate */
--color3: #8B4513;
/* SaddleBrown */
--color4: #FFA07A;
/* LightSalmon */
--bcolor1: #FFF8DC;
/* Cornsilk */
--bcolor2: #2F4F4F;
/* DarkSlateGray */
--bcolor3: #3E2723;
/* Darker brown */
--bcolor4: #4E342E;
/* Slightly lighter brown */
}
.navbar {
font-weight: 600;
color: var(--bcolor1);
background-color: var(--color1);
font-family: "Playfair Display", serif;
}
.navbar li a {
font-weight: 500;
color: var(--bcolor1);
font-family: "Playfair Display", serif;
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor1);
background-color: var(--color3);
font-weight: 500;
font-family: "Playfair Display", serif;
}
.footer a {
color: var(--color4);
text-decoration: none;
font-weight: 400;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-3.svg.j2";
}
.folders a {
font-weight: 600;
color: var(--bcolor1);
text-decoration: none;
font-family: "Playfair Display", serif;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color2);
text-decoration: none;
font-family: "Playfair Display", serif;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 400;
background-color: var(--bcolor2);
font-family: "Playfair Display", serif;
}
.tagentry label:hover {
background-color: var(--color3);
}
.tagentry .tagtoggle:hover {
background-color: var(--color3);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 600;
font-family: "Playfair Display", serif;
}
.loader,
.loader:before,
.loader:after {
border-radius: 50%;
width: 2.5em;
height: 2.5em;
animation-fill-mode: both;
animation: bblFadInOut 1.8s infinite ease-in-out;
}
.loader {
color: var(--bcolor2);
font-size: 7px;
position: relative;
text-indent: -9999em;
transform: translateZ(0);
animation-delay: -0.16s;
}
.loader:before,
.loader:after {
content: '';
position: absolute;
top: 0;
}
.loader:before {
left: -3.5em;
animation-delay: -0.32s;
}
.loader:after {
left: 3.5em;
}
@keyframes bblFadInOut {
0%,
80%,
100% {
box-shadow: 0 2.5em 0 -1.3em
}
40% {
box-shadow: 0 2.5em 0 0
}
}
body {
color: var(--bcolor1);
background-color: var(--bcolor3);
font-family: "Playfair Display", serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}

View File

@@ -1,135 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Montserrat:ital,wght@0,100..900;1,100..900&display=swap");
* {
--color1: #8b0000;
--color2: #b22222;
--color3: #ff4500;
--color4: #6e0000;
--bcolor1: #171717;
--bcolor2: #191919;
--bcolor3: #ebebeb;
--bcolor4: #0a0a0a;
}
.navbar {
font-weight: bold;
color: var(--bcolor3);
background-color: var(--color1);
font-weight: 900;
}
.navbar li a {
font-weight: 800;
color: var(--bcolor3);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor3);
background-color: var(--color3);
font-weight: 700;
}
.footer a {
color: var(--color4);
text-decoration: none;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-1.svg.j2";
}
.folders a {
font-weight: 800;
color: var(--bcolor1);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 800;
color: var(--color2);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 600;
background-color: var(--bcolor2);
}
.tagentry label:hover {
background-color: var(--bcolor4);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor4);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 800;
}
.loader {
width: 12px;
height: 12px;
border-radius: 50%;
display: block;
margin: 15px auto;
position: relative;
color: var(--color1);
box-sizing: border-box;
animation: animloader 1s linear infinite alternate;
}
@keyframes animloader {
0% {
box-shadow: -38px -12px, -14px 0, 14px 0, 38px 0;
}
33% {
box-shadow: -38px 0px, -14px -12px, 14px 0, 38px 0;
}
66% {
box-shadow: -38px 0px, -14px 0, 14px -12px, 38px 0;
}
100% {
box-shadow: -38px 0, -14px 0, 14px 0, 38px -12px;
}
}
body {
color: var(--bcolor1);
background-color: var(--bcolor3);
font-family: "Montserrat", sans-serif;
font-optical-sizing: auto;
font-weight: 700;
font-style: normal;
}

View File

@@ -1,198 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Nunito:wght@300;400;500;600;700&display=swap");
* {
--color1: #F28FAD;
--color2: #ABE9B3;
--color3: #FAE3B0;
--color4: #96CDFB;
--bcolor1: #F5E0DC;
--bcolor2: #575268;
--bcolor3: #D9E0EE;
--bcolor4: #C9CBFF;
}
.navbar {
font-weight: 600;
color: var(--bcolor2);
background-color: var(--color1);
font-family: "Nunito", sans-serif;
}
.navbar li a {
font-weight: 500;
color: var(--bcolor2);
font-family: "Nunito", sans-serif;
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor2);
background-color: var(--color3);
font-weight: 500;
font-family: "Nunito", sans-serif;
}
.footer a {
color: var(--color1);
text-decoration: none;
font-weight: 400;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/catpuccin.svg.j2";
}
.folders a {
font-weight: 600;
color: var(--bcolor2);
text-decoration: none;
font-family: "Nunito", sans-serif;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color1);
text-decoration: none;
font-family: "Nunito", sans-serif;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 400;
background-color: var(--color3);
font-family: "Nunito", sans-serif;
}
.tagentry label:hover {
background-color: var(--color4);
}
.tagentry .tagtoggle:hover {
background-color: var(--color4);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
color: var(--bcolor2);
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 600;
font-family: "Nunito", sans-serif;
}
.loader {
transform: rotateZ(45deg);
perspective: 1000px;
border-radius: 50%;
width: 48px;
height: 48px;
color: var(--color1);
}
.loader:before,
.loader:after {
content: '';
display: block;
position: absolute;
top: 0;
left: 0;
width: inherit;
height: inherit;
border-radius: 50%;
transform: rotateX(70deg);
animation: 1s spin linear infinite;
}
.loader:after {
color: var(--bcolor4);
transform: rotateY(70deg);
animation-delay: .4s;
}
@keyframes rotate {
0% {
transform: translate(-50%, -50%) rotateZ(0deg);
}
100% {
transform: translate(-50%, -50%) rotateZ(360deg);
}
}
@keyframes rotateccw {
0% {
transform: translate(-50%, -50%) rotate(0deg);
}
100% {
transform: translate(-50%, -50%) rotate(-360deg);
}
}
@keyframes spin {
0%,
100% {
box-shadow: .2em 0px 0 0px currentcolor;
}
12% {
box-shadow: .2em .2em 0 0 currentcolor;
}
25% {
box-shadow: 0 .2em 0 0px currentcolor;
}
37% {
box-shadow: -.2em .2em 0 0 currentcolor;
}
50% {
box-shadow: -.2em 0 0 0 currentcolor;
}
62% {
box-shadow: -.2em -.2em 0 0 currentcolor;
}
75% {
box-shadow: 0px -.2em 0 0 currentcolor;
}
87% {
box-shadow: .2em -.2em 0 0 currentcolor;
}
}
body {
color: var(--bcolor2);
background-color: var(--bcolor3);
font-family: "Nunito", sans-serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}

View File

@@ -1,135 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Montserrat:ital,wght@0,100..900;1,100..900&display=swap");
* {
--color1: cornflowerblue;
--color2: #1346a4;
--color3: #0e3377;
--color4: #3674e7;
--bcolor1: #171717;
--bcolor2: #191919;
--bcolor3: #ebebeb;
--bcolor4: #0a0a0a;
}
.navbar {
font-weight: bold;
color: var(--bcolor3);
background-color: var(--color1);
font-weight: 900;
}
.navbar li a {
font-weight: 800;
color: var(--bcolor3);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor3);
background-color: var(--color3);
font-weight: 700;
}
.footer a {
color: var(--color4);
text-decoration: none;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-1.svg.j2";
}
.folders a {
font-weight: 800;
color: var(--bcolor1);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 800;
color: var(--color2);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 600;
background-color: var(--bcolor2);
}
.tagentry label:hover {
background-color: var(--bcolor4);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor4);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 800;
}
.loader {
width: 12px;
height: 12px;
border-radius: 50%;
display: block;
margin: 15px auto;
position: relative;
color: var(--color1);
box-sizing: border-box;
animation: animloader 1s linear infinite alternate;
}
@keyframes animloader {
0% {
box-shadow: -38px -12px, -14px 0, 14px 0, 38px 0;
}
33% {
box-shadow: -38px 0px, -14px -12px, 14px 0, 38px 0;
}
66% {
box-shadow: -38px 0px, -14px 0, 14px -12px, 38px 0;
}
100% {
box-shadow: -38px 0, -14px 0, 14px 0, 38px -12px;
}
}
body {
color: var(--bcolor1);
background-color: var(--bcolor3);
font-family: "Montserrat", sans-serif;
font-optical-sizing: auto;
font-weight: 700;
font-style: normal;
}

View File

@@ -1,111 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Ubuntu:ital,wght@0,300;0,400;0,500;0,700;1,300;1,400;1,500;1,700&display=swap");
* {
--color1: #262a2b;
--color2: #0d0e0e;
--color3: #313537;
--color4: #181a1b;
--color5: #5483ef;
--bcolor1: #e8e6e3;
--bcolor2: #0c0d0e;
}
.navbar {
font-weight: bold;
color: var(--bcolor1);
background-color: var(--color1);
}
.navbar li a {
font-weight: bold;
color: var(--bcolor1);
}
/* Change the link color on hover */
.navbar li a:hover {
background-color: var(--color2);
}
.footer {
color: var(--bcolor1);
background-color: var(--color3);
font-weight: 500;
}
.footer a {
color: var(--color5);
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-2.svg.j2";
}
.folders a {
font-weight: 700;
color: var(--color5);
text-decoration: none;
}
.tooltiptext {
font-weight: 400;
background-color: var(--color3);
}
.tagentry label:hover {
background-color: var(--color4);
}
.tagentry .tagtoggle:hover {
background-color: var(--color4);
}
.column img {
background-color: var(--bcolor2);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 800;
}
.loader {
width: 48px;
height: 48px;
border-radius: 50%;
display: inline-block;
border-top: 3px solid var(--bcolor1);
border-right: 3px solid transparent;
box-sizing: border-box;
animation: rotation 1s linear infinite;
}
@keyframes rotation {
0% {
transform: rotate(0deg);
}
100% {
transform: rotate(360deg);
}
}
body {
color: var(--bcolor1);
background-color: var(--color4);
font-family: "Ubuntu", sans-serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}
body a {
font-weight: 400;
color: var(--color5);
text-decoration: none;
}

View File

@@ -1,111 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Ubuntu:ital,wght@0,300;0,400;0,500;0,700;1,300;1,400;1,500;1,700&display=swap");
* {
--color1: #333333;
--color2: #888888;
--color3: #dddddd;
--color4: #111111;
--color5: #0055ff;
--bcolor1: #ffffff;
--bcolor2: #000000;
}
.navbar {
font-weight: bold;
color: var(--bcolor1);
background-color: var(--color1);
}
.navbar li a {
font-weight: 700;
color: var(--bcolor1);
}
/* Change the link color on hover */
.navbar li a:hover {
background-color: var(--color4);
}
.footer {
color: var(--bcolor2);
background-color: var(--color3);
font-weight: 500;
}
.footer a {
color: var(--color5);
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-2.svg.j2";
}
.folders a {
font-weight: 700;
color: var(--color5);
text-decoration: none;
}
.tooltiptext {
font-weight: 400;
background-color: var(--color2);
}
.tagentry label:hover {
background-color: var(--color4);
}
.tagentry .tagtoggle:hover {
background-color: var(--color4);
}
.column img {
background-color: var(--color2);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 800;
}
.loader {
width: 48px;
height: 48px;
border-radius: 50%;
display: inline-block;
border-top: 3px solid var(--bcolor2);
border-right: 3px solid transparent;
box-sizing: border-box;
animation: rotation 1s linear infinite;
}
@keyframes rotation {
0% {
transform: rotate(0deg);
}
100% {
transform: rotate(360deg);
}
}
body {
color: var(--bcolor2);
background-color: var(--bcolor1);
font-family: "Ubuntu", sans-serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}
body a {
font-weight: 400;
color: var(--color5);
text-decoration: none;
}

View File

@@ -1,6 +0,0 @@
<svg width='64' height='64' viewBox='0 0 24 24' fill='none' xmlns='http://www.w3.org/2000/svg'>
<path d='M20 6H10L8 4H4C2.89543 4 2 4.89543 2 6V18C2 19.1046 2.89543 20 4 20H20C21.1046 20 22 19.1046 22 18V8C22 6.89543 21.1046 6 20 6Z' fill='{{ color1 }}' />
<path d='M4 4H8L10 6H20C21.1046 6 22 6.89543 22 8H2C2 6.89543 2.89543 6 4 6V4Z' fill='{{ color4 }}' />
<path d='M10 6H14L12 4H8L10 6Z' fill='{{ color3 }}' />
<path d='M14 6H18L16 4H12L14 6Z' fill='{{ color2 }}' />
</svg>

Before

Width:  |  Height:  |  Size: 493 B

View File

@@ -1,13 +0,0 @@
<?xml version="1.0" encoding="iso-8859-1"?>
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 48 48" style="enable-background:new 0 0 48 48;" xml:space="preserve">
<path style="fill:{{ color2 }};" d="M44.5,41h-41C2.119,41,1,39.881,1,38.5v-31C1,6.119,2.119,5,3.5,5h11.597
c1.519,0,2.955,0.69,3.904,1.877L21.5,10h23c1.381,0,2.5,1.119,2.5,2.5v26C47,39.881,45.881,41,44.5,41z" />
<path style="fill:{{ color2 }};" d="M2,25h20V11H4c-1.105,0-2,0.895-2,2V25z" />
<path style="fill:#FFFFFF;" d="M2,26h20V12H4c-1.105,0-2,0.895-2,2V26z" />
<path style="fill:{{ color1 }};" d="M1,37.875V38.5C1,39.881,2.119,41,3.5,41h41c1.381,0,2.5-1.119,2.5-2.5v-0.625H1z" />
<path style="fill:{{ color2 }};"
d="M44.5,11h-23l-1.237,0.824C19.114,12.591,17.763,13,16.381,13H3.5C2.119,13,1,14.119,1,15.5v22C1,38.881,2.119,40,3.5,40h41c1.381,0,2.5-1.119,2.5-2.5v-24C47,12.119,45.881,11,44.5,11z" />
<path style="fill:{{ color1 }};" d="M44.5,40h-41C2.119,40,1,38.881,1,37.5v-21C1,15.119,2.119,14,3.5,14h13.256
c1.382,0,2.733-0.409,3.883-1.176L21.875,12H44.5c1.381,0,2.5,1.119,2.5,2.5v23C47,38.881,45.881,40,44.5,40z" />
</svg>

Before

Width:  |  Height:  |  Size: 1.2 KiB

View File

@@ -1,11 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<svg width="800px" height="800px" viewBox="0 0 512 512" xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img"
preserveAspectRatio="xMidYMid meet">
<path fill="{{ color2 }}"
d="M491 326V92.143C491 79.021 480.259 68 467.137 68H341.13c-9.287 0-17.723 5.603-21.596 14.044l-12.709 27.903C302.952 118.388 294.516 124 285.229 124H67.538C54.416 124 44 134.426 44 147.549v216.363C44 377.034 54.416 388 67.538 388h399.599c.628 0 1.248-.36 1.863-.408V433h.342c0 6 4.877 10.636 10.829 10.636c5.952 0 10.829-4.967 10.829-10.919V326z">
</path>
<path fill="{{ color1 }}"
d="M480.171 443.636c-5.952 0-10.829-4.636-10.829-10.636H469V210.181C469 197.058 458.661 186 445.539 186H45.94C32.818 186 22 197.058 22 210.181V449.37C22 462.492 32.818 473 45.94 473h399.599c1.385 0 2.741-.06 4.061-.288c1.639.227 3.31.385 5.012.385c20.04 0 36.136-16.229 36.136-36.269c0-.534-.036-1.058-.058-1.586c-1.147 4.766-5.435 8.394-10.519 8.394z">
</path>
</svg>

Before

Width:  |  Height:  |  Size: 1.0 KiB

View File

@@ -1,34 +0,0 @@
<svg height="200px" width="200px" version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="-51.2 -51.2 614.40 614.40" xml:space="preserve"
fill="#000000" stroke="#000000" stroke-width="0.00512" transform="matrix(1, 0, 0, 1, 0, 0)rotate(0)">
<g id="SVGRepo_bgCarrier" stroke-width="0"></g>
<g id="SVGRepo_tracerCarrier" stroke-linecap="round" stroke-linejoin="round" stroke="#CCCCCC" stroke-width="10.24">
</g>
<g id="SVGRepo_iconCarrier">
<g transform="translate(0 1)">
<path style="fill: {{ color2 }};"
d="M422.4,144.067c0-18.773-13.653-34.133-29.867-34.133h-107.52l-37.547-51.2H81.92 c-11.947,0-22.187,11.947-22.187,25.6v59.733H422.4z"></path>
<path style="fill: {{ color3 }};" d="M426.667,109.933h-34.133c16.213,0,29.867,15.36,29.867,34.133h38.4 C460.8,125.293,445.44,109.933,426.667,109.933"></path>
<path style="fill: rgb(255, 255, 255);"
d="M81.92,58.733H59.733c-14.507,0-25.6,11.947-25.6,25.6v59.733h25.6V84.333 C59.733,70.68,69.973,58.733,81.92,58.733"></path>
<path style="fill: {{ color1 }};"
d="M34.133,169.667v256c0,14.507,10.24,25.6,23.04,25.6h397.653c12.8,0,23.04-11.093,23.04-25.6v-256 c0-14.507-10.24-25.6-23.04-25.6H57.173C44.373,144.067,34.133,156.013,34.133,169.667">
</path>
<path style="fill: rgb(255, 255, 255);"
d="M34.133,425.667v-256c0-14.507,10.24-25.6,23.04-25.6h-23.04c-14.507,0-25.6,11.093-25.6,25.6v256 c0,14.507,11.093,25.6,25.6,25.6h23.04C44.373,451.267,34.133,440.173,34.133,425.667">
</path>
<path style="fill: {{ color2 }};"
d="M477.867,144.067h-23.04c12.8,0,23.04,11.093,23.04,25.6v256c0,14.507-10.24,25.6-23.04,25.6h23.04 c14.507,0,25.6-11.093,25.6-25.6v-256C503.467,156.013,492.373,144.067,477.867,144.067">
</path>
<path
d="M477.867,459.8H34.133C15.36,459.8,0,444.44,0,425.667v-51.2c0-5.12,3.413-8.533,8.533-8.533s8.533,3.413,8.533,8.533v51.2 c0,9.387,7.68,17.067,17.067,17.067h443.733c9.387,0,17.067-7.68,17.067-17.067v-256c0-9.387-7.68-17.067-17.067-17.067H34.133 c-9.387,0-17.067,7.68-17.067,17.067V306.2c0,5.12-3.413,8.533-8.533,8.533S0,311.32,0,306.2V169.667 c0-18.773,15.36-34.133,34.133-34.133h443.733c18.773,0,34.133,15.36,34.133,34.133v256C512,444.44,496.64,459.8,477.867,459.8z">
</path>
<path d="M17.067,340.333c0-5.12-3.413-8.533-8.533-8.533S0,335.213,0,340.333c0,5.12,3.413,8.533,8.533,8.533 S17.067,345.453,17.067,340.333"></path>
<path
d="M460.8,152.6H34.133c-5.12,0-8.533-3.413-8.533-8.533V84.333C25.6,65.56,40.96,50.2,59.733,50.2h187.733 c2.56,0,5.12,0.853,6.827,3.413L294.4,101.4h132.267c23.893,0,42.667,18.773,42.667,42.667 C469.333,149.187,465.92,152.6,460.8,152.6z M42.667,135.533H450.56c-3.413-10.24-12.8-17.067-23.893-17.067H290.133 c-2.56,0-5.12-0.853-6.827-3.413L243.2,67.267H59.733c-9.387,0-17.067,7.68-17.067,17.067V135.533z">
</path>
<path d="M162.133,203.8h-102.4c-5.12,0-8.533-3.413-8.533-8.533c0-5.12,3.413-8.533,8.533-8.533h102.4 c5.12,0,8.533,3.413,8.533,8.533C170.667,200.387,167.253,203.8,162.133,203.8z"></path>
<path d="M162.133,237.933h-102.4c-5.12,0-8.533-3.413-8.533-8.533c0-5.12,3.413-8.533,8.533-8.533h102.4 c5.12,0,8.533,3.413,8.533,8.533C170.667,234.52,167.253,237.933,162.133,237.933z">
</path>
</g>
</g>
</svg>

Before

Width:  |  Height:  |  Size: 3.4 KiB

View File

@@ -1 +0,0 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 48 48" width="48px" height="48px"><linearGradient id="WQEfvoQAcpQgQgyjQQ4Hqa" x1="24" x2="24" y1="6.708" y2="14.977" gradientUnits="userSpaceOnUse"><stop offset="0" stop-color="#eba600"/><stop offset="1" stop-color="#c28200"/></linearGradient><path fill="url(#WQEfvoQAcpQgQgyjQQ4Hqa)" d="M24.414,10.414l-2.536-2.536C21.316,7.316,20.553,7,19.757,7L5,7C3.895,7,3,7.895,3,9l0,30 c0,1.105,0.895,2,2,2l38,0c1.105,0,2-0.895,2-2V13c0-1.105-0.895-2-2-2l-17.172,0C25.298,11,24.789,10.789,24.414,10.414z"/><linearGradient id="WQEfvoQAcpQgQgyjQQ4Hqb" x1="24" x2="24" y1="10.854" y2="40.983" gradientUnits="userSpaceOnUse"><stop offset="0" stop-color="#ffd869"/><stop offset="1" stop-color="#fec52b"/></linearGradient><path fill="url(#WQEfvoQAcpQgQgyjQQ4Hqb)" d="M21.586,14.414l3.268-3.268C24.947,11.053,25.074,11,25.207,11H43c1.105,0,2,0.895,2,2v26 c0,1.105-0.895,2-2,2H5c-1.105,0-2-0.895-2-2V15.5C3,15.224,3.224,15,3.5,15h16.672C20.702,15,21.211,14.789,21.586,14.414z"/></svg>

Before

Width:  |  Height:  |  Size: 1020 B

View File

@@ -1,10 +0,0 @@
<svg xmlns="http://www.w3.org/2000/svg" width="64" height="64" version="1">
<rect style="opacity:0.2" width="56" height="36" x="4" y="22" rx="2.8" ry="2.8" />
<path style="fill:{{ color2 }}"
d="M 4,46.2 C 4,47.751 5.2488,49 6.8,49 H 57.2 C 58.751,49 60,47.751 60,46.2 V 15.8 C 60,14.249 58.751,13 57.2,13 H 32 C 27.8,13 26.4,7 22.2,7 H 6.8 C 5.2488,7 4,8.2488 4,9.8" />
<rect style="opacity:0.2" width="56" height="36" x="4" y="20" rx="2.8" ry="2.8" />
<rect style="fill:#e4e4e4" width="48" height="22" x="8" y="16" rx="2.8" ry="2.8" />
<rect style="fill:{{ color1 }}" width="56" height="36" x="4" y="21" rx="2.8" ry="2.8" />
<path style="opacity:0.1;fill:#ffffff"
d="M 6.8008,7 C 5.2496,7 4,8.2496 4,9.8008 V 10.801 C 4,9.2496 5.2496,8 6.8008,8 H 22.199 C 26.399,8 27.8,14 32,14 H 57.199 C 58.75,14 60,15.25 60,16.801 V 15.801 C 60,14.25 58.75,13 57.199,13 H 32 C 27.8,13 26.399,7 22.199,7 Z" />
</svg>

Before

Width:  |  Height:  |  Size: 943 B

View File

@@ -1,11 +0,0 @@
<?xml version='1.0' encoding='UTF-8' standalone='no'?>
<svg height='512' width='512' version='1.1' id='Layer_1' viewBox='0 0 327.68 327.68' xml:space='preserve' xmlns='http://www.w3.org/2000/svg'
xmlns:svg='http://www.w3.org/2000/svg'>
<defs id='defs1' />
<g id='icon' transform='translate(-128.08785,-19.123746)'>
<path id='fg' style='fill:#dcdedf;fill-opacity:1;stroke:none;stroke-width:6.4;stroke-linecap:round'
d='m 428.2793,160.97461 c -78.34525,0.002 -156.69075,-0.007 -235.03585,0.0159 -6.54719,0.16827 -12.82625,4.35683 -15.37415,10.41233 -1.13922,2.74038 -1.79474,5.64883 -2.74311,8.45618 -10.27476,33.32809 -20.56379,66.65251 -30.78952,99.99526 -1.21885,4.66702 0.98496,9.97729 5.17832,12.3776 2.40372,1.49255 5.31559,1.67974 8.07056,1.58986 78.16762,-0.0305 156.33557,0.008 234.503,-0.0259 6.43644,-0.17102 12.61041,-4.22124 15.23762,-10.1162 1.2077,-2.75858 1.84495,-5.72012 2.81312,-8.56426 10.08283,-32.66775 20.13843,-65.34481 30.20361,-98.01744 0.84274,-2.37238 1.35887,-4.96865 0.67937,-7.45078 -0.98831,-4.2533 -4.6015,-7.82876 -8.96172,-8.48315 -1.24947,-0.20685 -2.51789,-0.23068 -3.78125,-0.18945 z' />
<path id='bg' style='fill:#dcdedf;fill-opacity:1;stroke:none;stroke-width:6.4;stroke-linecap:round;stroke-linejoin:miter;stroke-dasharray:none;stroke-opacity:1;paint-order:normal'
d='m 214.44922,72.089844 c -20.32611,0.01324 -40.65359,-0.03032 -60.97883,0.03325 -5.06767,0.228794 -9.72081,4.176673 -10.64873,9.186171 -0.54368,2.865585 -0.16202,5.794266 -0.28069,8.688777 -4.6e-4,27.527908 -0.008,55.056498 0.0176,82.583978 0.17186,3.22428 3.44977,5.89016 6.64757,5.28488 2.4037,-0.30447 4.32209,-2.31086 4.87898,-4.61617 3.53052,-10.60549 6.98896,-21.23707 10.60492,-31.81263 1.14174,-2.71356 4.14972,-4.41014 7.06111,-4.12697 16.80704,-0.0631 33.61433,-0.01 50.42149,-0.0279 55.72175,-0.002 111.44406,0.006 167.16547,-0.0191 5.71319,-0.19462 10.82844,-5.25566 10.91838,-11.00339 0.12602,-2.9908 -0.0352,-5.98579 0.0574,-8.97822 0.0534,-2.61272 -0.3941,-5.33067 -1.94259,-7.50013 -2.21535,-3.37352 -6.26106,-5.45808 -10.30253,-5.1988 -44.42303,-0.0315 -88.8461,0.006 -133.26914,-0.0339 -1.35699,0.0355 -2.86726,0.10531 -3.94821,-0.87625 -1.14131,-0.86056 -1.57137,-2.31551 -1.50179,-3.694889 -0.0148,-5.79966 0.0803,-11.603104 -0.0604,-17.400318 -0.41681,-5.210159 -4.80455,-9.807583 -10.02134,-10.361315 -2.37314,-0.240789 -4.76368,-0.0457 -7.14443,-0.12428 -5.89141,-0.0074 -11.78281,-0.0066 -17.67422,-0.0028 z' />
</g>
</svg>

Before

Width:  |  Height:  |  Size: 2.5 KiB

View File

@@ -1,46 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
width="100"
height="100"
viewBox="0 0 100 100"
version="1.1"
id="svg3"
xmlns="http://www.w3.org/2000/svg"
xmlns:svg="http://www.w3.org/2000/svg">
<rect
x="10"
y="30"
width="80"
height="50"
fill="{{ color1 }}"
rx="5"
ry="5"
id="rect1" />
<rect
x="10"
y="20"
width="40"
height="20"
fill="{{ color1 }}"
rx="5"
ry="5"
id="rect2" />
<rect
x="20"
y="40"
width="60"
height="40"
fill="{{ color2 }}"
rx="3"
ry="3"
id="rect3" />
<rect
x="30"
y="50"
width="40"
height="30"
fill="{{ color1 }}"
rx="2"
ry="2"
id="rect4" />
</svg>

Before

Width:  |  Height:  |  Size: 876 B

View File

@@ -1,27 +0,0 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Themes</title>
</head>
<body><a href="previews/alpenglow-dark.html">alpenglow-dark</a><br>
<a href="previews/alpenglow.html">alpenglow</a><br>
<a href="previews/aritim-dark.html">aritim-dark</a><br>
<a href="previews/aritim.html">aritim</a><br>
<a href="previews/autumn.html">autumn</a><br>
<a href="previews/carnation.html">carnation</a><br>
<a href="previews/catpuccin.html">catpuccin</a><br>
<a href="previews/cornflower.html">cornflower</a><br>
<a href="previews/default-dark.html">default-dark</a><br>
<a href="previews/default.html">default</a><br>
<a href="previews/ivy.html">ivy</a><br>
<a href="previews/kjoe.html">kjoe</a><br>
<a href="previews/monokai-vibrant.html">monokai-vibrant</a><br>
<a href="previews/rainbow.html">rainbow</a><br>
<a href="previews/spring.html">spring</a><br>
<a href="previews/steam.html">steam</a><br>
<a href="previews/summer.html">summer</a><br>
<a href="previews/sunflower.html">sunflower</a><br>
<a href="previews/winter.html">winter</a><br>
</body></html>

View File

@@ -1,133 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Montserrat:ital,wght@0,100..900;1,100..900&display=swap");
* {
--color1: #006400;
--color2: #008000;
--color3: #32cd32;
--color4: #004300;
--bcolor1: #171717;
--bcolor2: #191919;
--bcolor3: #ebebeb;
--bcolor4: #0a0a0a;
}
.navbar {
font-weight: bold;
color: var(--bcolor3);
background-color: var(--color1);
font-weight: 900;
}
.navbar li a {
font-weight: 800;
color: var(--bcolor3);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor3);
background-color: var(--color3);
font-weight: 700;
}
.footer a {
color: var(--color4);
text-decoration: none;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-1.svg.j2";
}
.folders a {
font-weight: 800;
color: var(--bcolor1);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 800;
color: var(--color2);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 600;
background-color: var(--bcolor2);
}
.tagentry label:hover {
background-color: var(--bcolor4);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor4);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
}
.loader {
width: 12px;
height: 12px;
border-radius: 50%;
display: block;
margin: 15px auto;
position: relative;
color: var(--color1);
box-sizing: border-box;
animation: animloader 1s linear infinite alternate;
}
@keyframes animloader {
0% {
box-shadow: -38px -12px, -14px 0, 14px 0, 38px 0;
}
33% {
box-shadow: -38px 0px, -14px -12px, 14px 0, 38px 0;
}
66% {
box-shadow: -38px 0px, -14px 0, 14px -12px, 38px 0;
}
100% {
box-shadow: -38px 0, -14px 0, 14px 0, 38px -12px;
}
}
body {
color: var(--bcolor1);
background-color: var(--bcolor3);
font-family: "Montserrat", sans-serif;
font-optical-sizing: auto;
font-weight: 700;
font-style: normal;
}

View File

@@ -1,134 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Montserrat:ital,wght@0,100..900;1,100..900&display=swap");
* {
--color1: #260000;
--color2: #470000;
--color3: #191313;
--color4: #ff2727;
--bcolor1: #ebebeb;
--bcolor2: #171717;
--bcolor3: #0a0a0a;
}
.navbar {
font-weight: bold;
color: var(--bcolor1);
background-color: var(--color1);
font-weight: 900;
}
.navbar li a {
font-weight: 800;
color: var(--bcolor1);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor1);
background-color: var(--color3);
font-weight: 700;
}
.footer a {
color: var(--color4);
text-decoration: none;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: url("data:image/svg+xml,%3Csvg width='800px' height='800px' viewBox='0 0 1024 1024' class='icon' version='1.1' xmlns='http://www.w3.org/2000/svg' fill='%23000000'%3E%3Cg id='SVGRepo_bgCarrier' stroke-width='0' /%3E%3Cg id='SVGRepo_tracerCarrier' stroke-linecap='round' stroke-linejoin='round' /%3E%3Cg id='SVGRepo_iconCarrier'%3E%3Cpath d='M853.333333 256H469.333333l-85.333333-85.333333H170.666667c-46.933333 0-85.333333 38.4-85.333334 85.333333v170.666667h853.333334v-85.333334c0-46.933333-38.4-85.333333-85.333334-85.333333z' fill='%238e0000' /%3E%3Cpath d='M853.333333 256H170.666667c-46.933333 0-85.333333 38.4-85.333334 85.333333v426.666667c0 46.933333 38.4 85.333333 85.333334 85.333333h682.666666c46.933333 0 85.333333-38.4 85.333334-85.333333V341.333333c0-46.933333-38.4-85.333333-85.333334-85.333333z' fill='%23FF2727' /%3E%3C/g%3E%3C/svg%3E");
}
.folders a {
font-weight: 800;
color: var(--bcolor1);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 800;
color: var(--color4);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 600;
background-color: var(--color3);
}
.tagentry label:hover {
background-color: var(--color2);
}
.tagentry .tagtoggle:hover {
background-color: var(--color2);
}
.column img {
background-color: var(--bcolor3);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 800;
}
.loader {
width: 12px;
height: 12px;
border-radius: 50%;
display: block;
margin: 15px auto;
position: relative;
color: var(--bcolor1);
box-sizing: border-box;
animation: animloader 1s linear infinite alternate;
}
@keyframes animloader {
0% {
box-shadow: -38px -12px, -14px 0, 14px 0, 38px 0;
}
33% {
box-shadow: -38px 0px, -14px -12px, 14px 0, 38px 0;
}
66% {
box-shadow: -38px 0px, -14px 0, 14px -12px, 38px 0;
}
100% {
box-shadow: -38px 0, -14px 0, 14px 0, 38px -12px;
}
}
body {
color: var(--bcolor1);
background-color: var(--bcolor2);
font-family: "Montserrat", sans-serif;
font-optical-sizing: auto;
font-weight: 700;
font-style: normal;
}

View File

@@ -1,178 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Montserrat:ital,wght@0,100..900;1,100..900&display=swap");
* {
--color1: #81f900;
--color2: #e542ff;
--color3: #ffd945;
--color4: #528bff;
--bcolor1: #f6f6f6;
--bcolor2: #2c313a;
--bcolor3: #191b20;
--bcolor4: #16171d;
--bcolor5: #0b0c0f;
}
.navbar {
font-weight: bold;
color: var(--bcolor1);
background-color: var(--bcolor3);
font-weight: 900;
}
.navbar li a {
font-weight: 900;
color: var(--bcolor1);
}
/* Change the link color on hover */
.navbar li a:hover {
background-color: var(--bcolor2);
}
.footer {
color: var(--bcolor1);
background-color: var(--bcolor2);
font-weight: 700;
}
.footer a {
color: var(--color4);
text-decoration: none;
}
.foldericon {
content: "themes/icons/subfolder.svg.j2";
}
.folders a {
font-weight: 900;
color: var(--color3);
text-decoration: none;
}
.tooltiptext {
font-weight: 600;
background-color: var(--bcolor2);
}
.tagentry label:hover {
background-color: var(--bcolor3);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor3);
}
.column img {
background-color: var(--bcolor5);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 800;
}
.loader {
transform: rotateZ(45deg);
perspective: 1000px;
border-radius: 50%;
width: 48px;
height: 48px;
color: var(--color2);
}
.loader:before,
.loader:after {
content: '';
display: block;
position: absolute;
top: 0;
left: 0;
width: inherit;
height: inherit;
border-radius: 50%;
transform: rotateX(70deg);
animation: 1s spin linear infinite;
}
.loader:after {
color: var(--color4);
transform: rotateY(70deg);
animation-delay: .4s;
}
@keyframes rotate {
0% {
transform: translate(-50%, -50%) rotateZ(0deg);
}
100% {
transform: translate(-50%, -50%) rotateZ(360deg);
}
}
@keyframes rotateccw {
0% {
transform: translate(-50%, -50%) rotate(0deg);
}
100% {
transform: translate(-50%, -50%) rotate(-360deg);
}
}
@keyframes spin {
0%,
100% {
box-shadow: .2em 0px 0 0px currentcolor;
}
12% {
box-shadow: .2em .2em 0 0 currentcolor;
}
25% {
box-shadow: 0 .2em 0 0px currentcolor;
}
37% {
box-shadow: -.2em .2em 0 0 currentcolor;
}
50% {
box-shadow: -.2em 0 0 0 currentcolor;
}
62% {
box-shadow: -.2em -.2em 0 0 currentcolor;
}
75% {
box-shadow: 0px -.2em 0 0 currentcolor;
}
87% {
box-shadow: .2em -.2em 0 0 currentcolor;
}
}
body {
color: var(--bcolor1);
background-color: var(--bcolor4);
font-family: "Montserrat", sans-serif;
font-optical-sizing: auto;
font-weight: 800;
font-style: normal;
}
body a {
font-weight: 900;
color: var(--color2);
text-decoration: none;
}

View File

@@ -1,138 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Montserrat:ital,wght@0,100..900;1,100..900&display=swap");
* {
--color5: #e50000;
--color6: #ff8d00;
--color3: #ffee00;
--color4: #028121;
--color1: #004cff;
--color2: #770088;
--bcolor1: #ebebeb;
--bcolor2: #191919;
--bcolor3: #171717;
--bcolor4: #0a0a0a;
--bcolor5: #929292;
}
.navbar {
font-weight: bold;
color: var(--bcolor1);
background-color: var(--color5);
font-weight: 900;
}
.navbar li a {
font-weight: 800;
color: var(--bcolor1);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color6);
}
.footer {
color: var(--bcolor2);
background-color: var(--color3);
font-weight: 700;
}
.footer a {
color: var(--color4);
text-decoration: none;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/subfolder.svg.j2";
}
.folders a {
font-weight: 800;
color: var(--bcolor3);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 800;
color: var(--color4);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 600;
background-color: var(--bcolor2);
}
.tagentry label:hover {
background-color: var(--bcolor4);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor4);
}
.column img {
background-color: var(--bcolor5);
}
#totop:hover {
background-color: var(--color3);
}
#totop {
background-color: var(--color6);
color: var(--bcolor4);
font-weight: 800;
}
.loader {
width: 12px;
height: 12px;
border-radius: 50%;
display: block;
margin: 15px auto;
position: relative;
color: var(--color4);
box-sizing: border-box;
animation: animloader 1s linear infinite alternate;
}
@keyframes animloader {
0% {
box-shadow: -38px -12px, -14px 0, 14px 0, 38px 0;
}
33% {
box-shadow: -38px 0px, -14px -12px, 14px 0, 38px 0;
}
66% {
box-shadow: -38px 0px, -14px 0, 14px -12px, 38px 0;
}
100% {
box-shadow: -38px 0, -14px 0, 14px 0, 38px -12px;
}
}
body {
color: var(--bcolor3);
background-color: var(--bcolor1);
font-family: "Montserrat", sans-serif;
font-optical-sizing: auto;
font-weight: 700;
font-style: normal;
}

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.0 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.0 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 MiB

View File

@@ -1,168 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Lora:wght@300;400;500;600;700&display=swap");
* {
--color1: #FFB6C1;
/* LightPink */
--color2: #98FB98;
/* PaleGreen */
--color3: #FFD700;
/* Gold */
--color4: #87CEFA;
/* LightSkyBlue */
--bcolor1: #FFFFFF;
/* White */
--bcolor2: #2F4F4F;
/* DarkSlateGray */
--bcolor3: #FAF0E6;
/* Linen */
--bcolor4: #E6E6FA;
/* Lavender */
}
.navbar {
font-weight: 600;
color: var(--bcolor2);
background-color: var(--color1);
font-family: "Lora", serif;
}
.navbar li a {
font-weight: 500;
color: var(--bcolor2);
font-family: "Lora", serif;
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor2);
background-color: var(--color3);
font-weight: 500;
font-family: "Lora", serif;
}
.footer a {
color: var(--color4);
text-decoration: none;
font-weight: 400;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-3.svg.j2";
}
.folders a {
font-weight: 600;
color: var(--bcolor2);
text-decoration: none;
font-family: "Lora", serif;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color2);
text-decoration: none;
font-family: "Lora", serif;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 400;
background-color: var(--bcolor4);
font-family: "Lora", serif;
}
.tagentry label:hover {
background-color: var(--bcolor3);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor3);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 600;
font-family: "Lora", serif;
}
.loader,
.loader:before,
.loader:after {
border-radius: 50%;
width: 2.5em;
height: 2.5em;
animation-fill-mode: both;
animation: bblFadInOut 1.8s infinite ease-in-out;
}
.loader {
color: var(--bcolor2);
font-size: 7px;
position: relative;
text-indent: -9999em;
transform: translateZ(0);
animation-delay: -0.16s;
}
.loader:before,
.loader:after {
content: '';
position: absolute;
top: 0;
}
.loader:before {
left: -3.5em;
animation-delay: -0.32s;
}
.loader:after {
left: 3.5em;
}
@keyframes bblFadInOut {
0%,
80%,
100% {
box-shadow: 0 2.5em 0 -1.3em
}
40% {
box-shadow: 0 2.5em 0 0
}
}
body {
color: var(--bcolor2);
background-color: var(--bcolor3);
font-family: "Lora", serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}

View File

@@ -1,158 +0,0 @@
@import url('https://fonts.cdnfonts.com/css/arial');
* {
--color1: #171d25;
--color2: #1a9fff;
--color3: #17191b;
--color4: #3d4450;
--bcolor1: #dcdedf;
--bcolor2: #262a32;
}
.navbar {
font-weight: 900;
color: var(--bcolor1);
background-color: var(--color1);
}
.navbar li a {
font-weight: 900;
color: var(--bcolor1);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: underline;
text-decoration-thickness: 0.3ex;
text-underline-offset: 0.5ex;
color: var(--color2)
}
.footer {
color: var(--bcolor1);
background-color: var(--color3);
font-weight: 500;
}
.footer a {
color: var(--color2);
text-decoration: none;
font-weight: 700;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: url("data:image/svg+xml,%3C%3Fxml version='1.0' encoding='UTF-8' standalone='no'%3F%3E%3Csvg height='512' width='512' version='1.1' id='Layer_1' viewBox='0 0 327.68 327.68' xml:space='preserve' xmlns='http://www.w3.org/2000/svg' xmlns:svg='http://www.w3.org/2000/svg'%3E%3Cdefs id='defs1' /%3E%3Cg id='icon' transform='translate(-128.08785,-19.123746)'%3E%3Cpath id='fg' style='fill:%23dcdedf;fill-opacity:1;stroke:none;stroke-width:6.4;stroke-linecap:round' d='m 428.2793,160.97461 c -78.34525,0.002 -156.69075,-0.007 -235.03585,0.0159 -6.54719,0.16827 -12.82625,4.35683 -15.37415,10.41233 -1.13922,2.74038 -1.79474,5.64883 -2.74311,8.45618 -10.27476,33.32809 -20.56379,66.65251 -30.78952,99.99526 -1.21885,4.66702 0.98496,9.97729 5.17832,12.3776 2.40372,1.49255 5.31559,1.67974 8.07056,1.58986 78.16762,-0.0305 156.33557,0.008 234.503,-0.0259 6.43644,-0.17102 12.61041,-4.22124 15.23762,-10.1162 1.2077,-2.75858 1.84495,-5.72012 2.81312,-8.56426 10.08283,-32.66775 20.13843,-65.34481 30.20361,-98.01744 0.84274,-2.37238 1.35887,-4.96865 0.67937,-7.45078 -0.98831,-4.2533 -4.6015,-7.82876 -8.96172,-8.48315 -1.24947,-0.20685 -2.51789,-0.23068 -3.78125,-0.18945 z' /%3E%3Cpath id='bg' style='fill:%23dcdedf;fill-opacity:1;stroke:none;stroke-width:6.4;stroke-linecap:round;stroke-linejoin:miter;stroke-dasharray:none;stroke-opacity:1;paint-order:normal' d='m 214.44922,72.089844 c -20.32611,0.01324 -40.65359,-0.03032 -60.97883,0.03325 -5.06767,0.228794 -9.72081,4.176673 -10.64873,9.186171 -0.54368,2.865585 -0.16202,5.794266 -0.28069,8.688777 -4.6e-4,27.527908 -0.008,55.056498 0.0176,82.583978 0.17186,3.22428 3.44977,5.89016 6.64757,5.28488 2.4037,-0.30447 4.32209,-2.31086 4.87898,-4.61617 3.53052,-10.60549 6.98896,-21.23707 10.60492,-31.81263 1.14174,-2.71356 4.14972,-4.41014 7.06111,-4.12697 16.80704,-0.0631 33.61433,-0.01 50.42149,-0.0279 55.72175,-0.002 111.44406,0.006 167.16547,-0.0191 5.71319,-0.19462 10.82844,-5.25566 10.91838,-11.00339 0.12602,-2.9908 -0.0352,-5.98579 0.0574,-8.97822 0.0534,-2.61272 -0.3941,-5.33067 -1.94259,-7.50013 -2.21535,-3.37352 -6.26106,-5.45808 -10.30253,-5.1988 -44.42303,-0.0315 -88.8461,0.006 -133.26914,-0.0339 -1.35699,0.0355 -2.86726,0.10531 -3.94821,-0.87625 -1.14131,-0.86056 -1.57137,-2.31551 -1.50179,-3.694889 -0.0148,-5.79966 0.0803,-11.603104 -0.0604,-17.400318 -0.41681,-5.210159 -4.80455,-9.807583 -10.02134,-10.361315 -2.37314,-0.240789 -4.76368,-0.0457 -7.14443,-0.12428 -5.89141,-0.0074 -11.78281,-0.0066 -17.67422,-0.0028 z' /%3E%3C/g%3E%3C/svg%3E%0A");
}
.folders a {
font-weight: 700;
color: var(--bcolor1);
text-decoration: none;
}
.folders figure:hover img {
content: url("data:image/svg+xml,%3C%3Fxml version='1.0' encoding='UTF-8' standalone='no'%3F%3E%3Csvg height='512' width='512' version='1.1' id='Layer_1' viewBox='0 0 327.68 327.68' xml:space='preserve' xmlns='http://www.w3.org/2000/svg' xmlns:svg='http://www.w3.org/2000/svg'%3E%3Cdefs id='defs1' /%3E%3Cg id='icon' transform='translate(-128.08785,-19.123746)'%3E%3Cpath id='fg' style='fill:%23dcdedf;fill-opacity:1;stroke:none;stroke-width:6.4;stroke-linecap:round' d='m 428.2793,160.97461 c -78.34525,0.002 -156.69075,-0.007 -235.03585,0.0159 -6.54719,0.16827 -12.82625,4.35683 -15.37415,10.41233 -1.13922,2.74038 -1.79474,5.64883 -2.74311,8.45618 -10.27476,33.32809 -20.56379,66.65251 -30.78952,99.99526 -1.21885,4.66702 0.98496,9.97729 5.17832,12.3776 2.40372,1.49255 5.31559,1.67974 8.07056,1.58986 78.16762,-0.0305 156.33557,0.008 234.503,-0.0259 6.43644,-0.17102 12.61041,-4.22124 15.23762,-10.1162 1.2077,-2.75858 1.84495,-5.72012 2.81312,-8.56426 10.08283,-32.66775 20.13843,-65.34481 30.20361,-98.01744 0.84274,-2.37238 1.35887,-4.96865 0.67937,-7.45078 -0.98831,-4.2533 -4.6015,-7.82876 -8.96172,-8.48315 -1.24947,-0.20685 -2.51789,-0.23068 -3.78125,-0.18945 z' /%3E%3Cpath id='bg' style='fill:%231a9fff;fill-opacity:1;stroke:none;stroke-width:6.4;stroke-linecap:round;stroke-linejoin:miter;stroke-dasharray:none;stroke-opacity:1;paint-order:normal' d='m 214.44922,72.089844 c -20.32611,0.01324 -40.65359,-0.03032 -60.97883,0.03325 -5.06767,0.228794 -9.72081,4.176673 -10.64873,9.186171 -0.54368,2.865585 -0.16202,5.794266 -0.28069,8.688777 -4.6e-4,27.527908 -0.008,55.056498 0.0176,82.583978 0.17186,3.22428 3.44977,5.89016 6.64757,5.28488 2.4037,-0.30447 4.32209,-2.31086 4.87898,-4.61617 3.53052,-10.60549 6.98896,-21.23707 10.60492,-31.81263 1.14174,-2.71356 4.14972,-4.41014 7.06111,-4.12697 16.80704,-0.0631 33.61433,-0.01 50.42149,-0.0279 55.72175,-0.002 111.44406,0.006 167.16547,-0.0191 5.71319,-0.19462 10.82844,-5.25566 10.91838,-11.00339 0.12602,-2.9908 -0.0352,-5.98579 0.0574,-8.97822 0.0534,-2.61272 -0.3941,-5.33067 -1.94259,-7.50013 -2.21535,-3.37352 -6.26106,-5.45808 -10.30253,-5.1988 -44.42303,-0.0315 -88.8461,0.006 -133.26914,-0.0339 -1.35699,0.0355 -2.86726,0.10531 -3.94821,-0.87625 -1.14131,-0.86056 -1.57137,-2.31551 -1.50179,-3.694889 -0.0148,-5.79966 0.0803,-11.603104 -0.0604,-17.400318 -0.41681,-5.210159 -4.80455,-9.807583 -10.02134,-10.361315 -2.37314,-0.240789 -4.76368,-0.0457 -7.14443,-0.12428 -5.89141,-0.0074 -11.78281,-0.0066 -17.67422,-0.0028 z' /%3E%3C/g%3E%3C/svg%3E%0A");
}
.folders a:hover {
text-decoration: underline;
text-decoration-thickness: 0.3ex;
text-underline-offset: 0.5ex;
color: var(--color2)
}
.row a {
font-weight: 500;
color: var(--color2);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 500;
background-color: var(--color4);
}
.tagentry label:hover {
background-color: var(--color3);
}
.tagentry .tagtoggle:hover {
background-color: var(--color3);
}
.column img {
background-color: var(--color4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 700;
}
.loader {
width: 48px;
height: 48px;
border-radius: 50%;
position: relative;
animation: rotate 1s linear infinite
}
.loader::before {
content: "";
box-sizing: border-box;
position: absolute;
inset: 0px;
border-radius: 50%;
border: 5px solid var(--color2);
animation: prixClipFix 2s linear infinite;
}
@keyframes rotate {
100% {
transform: rotate(360deg)
}
}
@keyframes prixClipFix {
0% {
clip-path: polygon(50% 50%, 0 0, 0 0, 0 0, 0 0, 0 0)
}
25% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 0, 100% 0, 100% 0)
}
50% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 100% 100%, 100% 100%)
}
75% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 0 100%, 0 100%)
}
100% {
clip-path: polygon(50% 50%, 0 0, 100% 0, 100% 100%, 0 100%, 0 0)
}
}
body {
color: var(--bcolor1);
background-color: var(--bcolor2);
font-family: "Arial", sans-serif;
font-optical-sizing: auto;
font-weight: 500;
font-style: normal;
}

View File

@@ -1,162 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Roboto:wght@300;400;500;700&display=swap");
* {
--color1: #FFD700; /* Gold */
--color2: #00BFFF; /* DeepSkyBlue */
--color3: #32CD32; /* LimeGreen */
--color4: #FFA500; /* Orange */
--bcolor1: #FFFFFF; /* White */
--bcolor2: #1E1E1E; /* DarkGrey */
--bcolor3: #F0F8FF; /* AliceBlue */
--bcolor4: #E0FFFF; /* LightCyan */
}
.navbar {
font-weight: 700;
color: var(--bcolor2);
background-color: var(--color1);
font-family: "Roboto", sans-serif;
}
.navbar li a {
font-weight: 500;
color: var(--bcolor2);
font-family: "Roboto", sans-serif;
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor1);
background-color: var(--color3);
font-weight: 500;
font-family: "Roboto", sans-serif;
}
.footer a {
color: var(--color4);
text-decoration: none;
font-weight: 400;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-3.svg.j2";
}
.folders a {
font-weight: 600;
color: var(--bcolor2);
text-decoration: none;
font-family: "Roboto", sans-serif;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color2);
text-decoration: none;
font-family: "Roboto", sans-serif;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 400;
color: var(--bcolor1);
background-color: var(--bcolor2);
font-family: "Roboto", sans-serif;
}
.tagentry label:hover {
background-color: var(--bcolor3);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor3);
color: var(--bcolor2);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 600;
font-family: "Roboto", sans-serif;
}
.loader,
.loader:before,
.loader:after {
border-radius: 50%;
width: 2.5em;
height: 2.5em;
animation-fill-mode: both;
animation: bblFadInOut 1.8s infinite ease-in-out;
}
.loader {
color: var(--bcolor2);
font-size: 7px;
position: relative;
text-indent: -9999em;
transform: translateZ(0);
animation-delay: -0.16s;
}
.loader:before,
.loader:after {
content: '';
position: absolute;
top: 0;
}
.loader:before {
left: -3.5em;
animation-delay: -0.32s;
}
.loader:after {
left: 3.5em;
}
@keyframes bblFadInOut {
0%,
80%,
100% {
box-shadow: 0 2.5em 0 -1.3em
}
40% {
box-shadow: 0 2.5em 0 0
}
}
body {
color: var(--bcolor2);
background-color: var(--bcolor3);
font-family: "Roboto", sans-serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}

View File

@@ -1,136 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Montserrat:ital,wght@0,100..900;1,100..900&display=swap");
* {
--color1: #ffb000;
--color2: #ffd700;
--color3: #ffe135;
--color4: #ce8c00;
--bcolor1: #171717;
--bcolor2: #191919;
--bcolor3: #ebebeb;
--bcolor4: #0a0a0a;
}
.navbar {
font-weight: bold;
color: var(--bcolor2);
background-color: var(--color1);
font-weight: 900;
}
.navbar li a {
font-weight: 800;
color: var(--bcolor2);
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor2);
background-color: var(--color3);
font-weight: 700;
}
.footer a {
color: var(--color4);
text-decoration: none;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-1.svg.j2";
}
.folders a {
font-weight: 800;
color: var(--bcolor1);
text-decoration: none;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 800;
color: var(--color1);
text-decoration: none;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 600;
color: var(--bcolor3);
background-color: var(--bcolor2);
}
.tagentry label:hover {
background-color: var(--bcolor4);
}
.tagentry .tagtoggle:hover {
background-color: var(--bcolor4);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 800;
}
.loader {
width: 12px;
height: 12px;
border-radius: 50%;
display: block;
margin: 15px auto;
position: relative;
color: var(--color1);
box-sizing: border-box;
animation: animloader 1s linear infinite alternate;
}
@keyframes animloader {
0% {
box-shadow: -38px -12px, -14px 0, 14px 0, 38px 0;
}
33% {
box-shadow: -38px 0px, -14px -12px, 14px 0, 38px 0;
}
66% {
box-shadow: -38px 0px, -14px 0, 14px -12px, 38px 0;
}
100% {
box-shadow: -38px 0, -14px 0, 14px 0, 38px -12px;
}
}
body {
color: var(--bcolor1);
background-color: var(--bcolor3);
font-family: "Montserrat", sans-serif;
font-optical-sizing: auto;
font-weight: 700;
font-style: normal;
}

View File

@@ -1,169 +0,0 @@
@import url("https://fonts.googleapis.com/css2?family=Montserrat:wght@300;400;500;600;700&display=swap");
* {
--color1: #00CED1;
/* DarkTurquoise */
--color2: #4682B4;
/* SteelBlue */
--color3: #B0C4DE;
/* LightSteelBlue */
--color4: #5F9EA0;
/* CadetBlue */
--bcolor1: #FFFFFF;
/* White */
--bcolor2: #2F4F4F;
/* DarkSlateGray */
--bcolor3: #E0E0E0;
/* LightGray */
--bcolor4: #D3D3D3;
/* LightGray */
}
.navbar {
font-weight: 600;
color: var(--bcolor2);
background-color: var(--color1);
font-family: "Montserrat", sans-serif;
}
.navbar li a {
font-weight: 500;
color: var(--bcolor2);
font-family: "Montserrat", sans-serif;
}
/* Change the link color on hover */
.navbar li a:hover {
text-decoration: none;
background-color: var(--color2);
}
.footer {
color: var(--bcolor2);
background-color: var(--color3);
font-weight: 500;
font-family: "Montserrat", sans-serif;
}
.footer a {
color: var(--color2);
text-decoration: none;
font-weight: 400;
}
.footer a:hover {
text-decoration: none;
}
.foldericon {
content: "themes/icons/folder-3.svg.j2";
}
.folders a {
font-weight: 600;
color: var(--bcolor2);
text-decoration: none;
font-family: "Montserrat", sans-serif;
}
.folders a:hover {
text-decoration: none;
}
.row a {
font-weight: 500;
color: var(--color2);
text-decoration: none;
font-family: "Montserrat", sans-serif;
}
.row a:hover {
text-decoration: underline;
}
.tooltiptext {
font-weight: 400;
color: var(--bcolor3);
background-color: var(--bcolor2);
font-family: "Montserrat", sans-serif;
}
.tagentry label:hover {
background-color: var(--color2);
}
.tagentry .tagtoggle:hover {
background-color: var(--color2);
}
.column img {
background-color: var(--bcolor4);
}
#totop:hover {
background-color: var(--color2);
}
#totop {
background-color: var(--color1);
color: var(--bcolor1);
font-weight: 600;
font-family: "Montserrat", sans-serif;
}
.loader,
.loader:before,
.loader:after {
border-radius: 50%;
width: 2.5em;
height: 2.5em;
animation-fill-mode: both;
animation: bblFadInOut 1.8s infinite ease-in-out;
}
.loader {
color: var(--bcolor2);
font-size: 7px;
position: relative;
text-indent: -9999em;
transform: translateZ(0);
animation-delay: -0.16s;
}
.loader:before,
.loader:after {
content: '';
position: absolute;
top: 0;
}
.loader:before {
left: -3.5em;
animation-delay: -0.32s;
}
.loader:after {
left: 3.5em;
}
@keyframes bblFadInOut {
0%,
80%,
100% {
box-shadow: 0 2.5em 0 -1.3em
}
40% {
box-shadow: 0 2.5em 0 0
}
}
body {
color: var(--bcolor2);
background-color: var(--bcolor3);
font-family: "Montserrat", sans-serif;
font-optical-sizing: auto;
font-weight: 400;
font-style: normal;
}