From a508079a36e89a0c14e0eea6451f78c3bd5756f0 Mon Sep 17 00:00:00 2001 From: Jesse Vincent Date: Fri, 5 Jun 2026 15:11:23 -0700 Subject: [PATCH 1/7] Add tag vocabulary + plumbing for topic/feature tags - tags_lib.py: shared parse/render helpers for .docs.md tag comments - tags.json: seed topic + feature vocabulary, injected into the LLM prompt - write_docs.py: LLM call now emits topics/features, merges new tags - gather_links.py: surfaces topics/features into tools.json - unit tests for both parsers --- gather_links.py | 16 +++++ tags.json | 45 ++++++++++++++ tags_lib.py | 84 ++++++++++++++++++++++++++ test_tags_lib.py | 69 +++++++++++++++++++++ test_write_docs.py | 41 +++++++++++++ write_docs.py | 146 ++++++++++++++++++++++++++++++++++----------- 6 files changed, 366 insertions(+), 35 deletions(-) create mode 100644 tags.json create mode 100644 tags_lib.py create mode 100644 test_tags_lib.py create mode 100644 test_write_docs.py diff --git a/gather_links.py b/gather_links.py index f2a925cb..6db1e3a7 100755 --- a/gather_links.py +++ b/gather_links.py @@ -7,6 +7,8 @@ from datetime import datetime import html +import tags_lib + def get_file_commit_details(file_path): """ @@ -92,6 +94,17 @@ def extract_description(docs_path: Path) -> str: return " ".join(lines) +def extract_tags(docs_path: Path): + """Return ``(topics, features)`` parsed from the generated docs file.""" + if not docs_path.exists(): + return [], [] + try: + content = docs_path.read_text("utf-8") + except OSError: + return [], [] + return tags_lib.parse_tags(content) + + def extract_title(html_path: Path) -> str: """Extract the from an HTML file.""" try: @@ -149,6 +162,7 @@ def main(): docs_path = html_file.with_suffix(".docs.md") description = extract_description(docs_path) + topics, features = extract_tags(docs_path) created_date = commits[-1]["date"] if commits else None updated_date = commits[0]["date"] if commits else None @@ -159,6 +173,8 @@ def main(): "slug": slug, "title": extract_title(html_file), "description": description, + "topics": topics, + "features": features, "created": created_date, "updated": updated_date, "url": f"/{slug}" if slug != "index" else "/", diff --git a/tags.json b/tags.json new file mode 100644 index 00000000..2908739b --- /dev/null +++ b/tags.json @@ -0,0 +1,45 @@ +{ + "topics": { + "ai-llm": "AI & LLMs", + "text-writing": "Text & Writing", + "data-json": "Data & JSON", + "images-graphics": "Images & Graphics", + "audio-video": "Audio & Video", + "maps-geo": "Maps & Geography", + "css-layout": "CSS & Layout Playgrounds", + "developer-tools": "Developer Tools", + "data-visualization": "Data Visualization", + "accessibility": "Accessibility", + "sqlite-databases": "SQLite & Databases", + "social-feeds": "Social & Feeds", + "productivity": "Productivity & Utilities", + "games-fun": "Games & Fun", + "encoding-security": "Encoding & Security", + "documents-pdf": "Documents & PDF", + "reference-education": "Reference & Education" + }, + "features": { + "clipboard": "Clipboard", + "canvas": "Canvas", + "webgl": "WebGL", + "svg": "SVG", + "web-audio": "Web Audio", + "speech": "Speech & Voice", + "file-upload": "File Upload", + "drag-and-drop": "Drag & Drop", + "local-storage": "Local Storage", + "indexeddb": "IndexedDB", + "camera-mic": "Camera & Microphone", + "geolocation": "Geolocation", + "webassembly": "WebAssembly", + "web-workers": "Web Workers", + "service-worker": "Service Worker", + "webrtc": "WebRTC", + "websockets": "WebSockets", + "fetch-network": "Network & Fetch", + "fullscreen": "Fullscreen", + "notifications": "Notifications", + "web-share": "Web Share", + "url-state": "URL State" + } +} diff --git a/tags_lib.py b/tags_lib.py new file mode 100644 index 00000000..3e114251 --- /dev/null +++ b/tags_lib.py @@ -0,0 +1,84 @@ +"""Shared helpers for reading and writing tag metadata in ``*.docs.md`` files. + +A generated docs file looks like:: + + <description paragraph> + + <!-- topics: developer-tools, data-json --> + <!-- features: clipboard, fetch-network --> + <!-- Generated from commit: <hash> --> + +The ``topics``/``features`` comment lines are optional so legacy docs files +(description + commit marker only) keep working unchanged. +""" + +from __future__ import annotations + +import json +import re +from pathlib import Path +from typing import List, Tuple + +COMMIT_MARKER_RE = re.compile(r"<!-- Generated from commit: ([a-f0-9]+) -->") +TOPICS_RE = re.compile(r"<!--\s*topics:(.*?)-->", re.IGNORECASE | re.DOTALL) +FEATURES_RE = re.compile(r"<!--\s*features:(.*?)-->", re.IGNORECASE | re.DOTALL) + +TAGS_PATH = Path(__file__).resolve().parent / "tags.json" + + +def _split_csv(value: str) -> List[str]: + return [item.strip() for item in value.split(",") if item.strip()] + + +def parse_tags(content: str) -> Tuple[List[str], List[str]]: + """Return ``(topics, features)`` parsed from a docs file's content.""" + topics_match = TOPICS_RE.search(content) + features_match = FEATURES_RE.search(content) + topics = _split_csv(topics_match.group(1)) if topics_match else [] + features = _split_csv(features_match.group(1)) if features_match else [] + return topics, features + + +def extract_description(content: str) -> str: + """Return the human description with every generated comment removed.""" + return content.split("<!--", 1)[0].strip() + + +def extract_commit_hash(content: str): + """Return the commit hash recorded in the docs file, or ``None``.""" + match = COMMIT_MARKER_RE.search(content) + return match.group(1) if match else None + + +def render_docs( + description: str, + *, + topics: List[str] | None = None, + features: List[str] | None = None, + commit_hash: str, +) -> str: + """Render a complete docs file from its parts.""" + parts = [description.strip(), ""] + if topics: + parts.append(f"<!-- topics: {', '.join(topics)} -->") + if features: + parts.append(f"<!-- features: {', '.join(features)} -->") + parts.append(f"<!-- Generated from commit: {commit_hash} -->") + return "\n".join(parts) + + +def load_vocabulary() -> dict: + """Load the canonical tag vocabulary from tags.json.""" + with TAGS_PATH.open("r", encoding="utf-8") as fp: + return json.load(fp) + + +def vocabulary_prompt_block() -> str: + """Format the vocabulary as a prompt fragment listing existing tags.""" + vocab = load_vocabulary() + topics = ", ".join(sorted(vocab.get("topics", {}))) + features = ", ".join(sorted(vocab.get("features", {}))) + return ( + f"Existing topic tags (prefer these): {topics}\n" + f"Existing feature tags (prefer these): {features}" + ) diff --git a/test_tags_lib.py b/test_tags_lib.py new file mode 100644 index 00000000..2ad382ec --- /dev/null +++ b/test_tags_lib.py @@ -0,0 +1,69 @@ +"""Unit tests for tags_lib: parsing and rendering tag metadata in .docs.md files.""" + +import tags_lib + + +DESCRIPTION = ( + "View Mozilla Bugzilla bug reports directly in your browser. Paste an ID " + "and the tool fetches and renders the report." +) + +DOCS_WITH_TAGS = f"""{DESCRIPTION} + +<!-- topics: developer-tools, data-json --> +<!-- features: clipboard, fetch-network --> +<!-- Generated from commit: abc123 -->""" + +DOCS_LEGACY = f"""{DESCRIPTION} + +<!-- Generated from commit: abc123 -->""" + + +def test_parse_tags_reads_topics_and_features(): + topics, features = tags_lib.parse_tags(DOCS_WITH_TAGS) + assert topics == ["developer-tools", "data-json"] + assert features == ["clipboard", "fetch-network"] + + +def test_parse_tags_missing_lines_returns_empty(): + topics, features = tags_lib.parse_tags(DOCS_LEGACY) + assert topics == [] + assert features == [] + + +def test_extract_description_strips_all_generated_comments(): + assert tags_lib.extract_description(DOCS_WITH_TAGS) == DESCRIPTION + assert tags_lib.extract_description(DOCS_LEGACY) == DESCRIPTION + + +def test_extract_commit_hash(): + assert tags_lib.extract_commit_hash(DOCS_WITH_TAGS) == "abc123" + assert tags_lib.extract_commit_hash("no marker here") is None + + +def test_render_docs_roundtrips(): + rendered = tags_lib.render_docs( + DESCRIPTION, + topics=["developer-tools", "data-json"], + features=["clipboard", "fetch-network"], + commit_hash="abc123", + ) + topics, features = tags_lib.parse_tags(rendered) + assert topics == ["developer-tools", "data-json"] + assert features == ["clipboard", "fetch-network"] + assert tags_lib.extract_description(rendered) == DESCRIPTION + assert tags_lib.extract_commit_hash(rendered) == "abc123" + + +def test_render_docs_omits_empty_tag_lines(): + rendered = tags_lib.render_docs(DESCRIPTION, topics=[], features=[], commit_hash="abc123") + assert "topics:" not in rendered + assert "features:" not in rendered + assert tags_lib.extract_description(rendered) == DESCRIPTION + + +def test_parse_tags_tolerates_extra_whitespace(): + content = "Desc\n\n<!-- topics: a , b -->\n<!--features:c-->\n" + topics, features = tags_lib.parse_tags(content) + assert topics == ["a", "b"] + assert features == ["c"] diff --git a/test_write_docs.py b/test_write_docs.py new file mode 100644 index 00000000..a707e23b --- /dev/null +++ b/test_write_docs.py @@ -0,0 +1,41 @@ +"""Unit tests for write_docs model-output parsing.""" + +import write_docs + + +def test_parse_model_output_splits_description_and_tags(): + output = ( + "View bug reports directly in your browser.\n" + "It fetches and renders them.\n" + 'TAGS: {"topics": ["developer-tools"], "features": ["clipboard", "fetch-network"]}' + ) + description, topics, features = write_docs.parse_model_output(output) + assert description == ( + "View bug reports directly in your browser.\nIt fetches and renders them." + ) + assert topics == ["developer-tools"] + assert features == ["clipboard", "fetch-network"] + + +def test_parse_model_output_without_tags_line(): + output = "A plain description with no tags." + description, topics, features = write_docs.parse_model_output(output) + assert description == "A plain description with no tags." + assert topics == [] + assert features == [] + + +def test_parse_model_output_malformed_tags_are_ignored(): + output = "Desc.\nTAGS: not json" + description, topics, features = write_docs.parse_model_output(output) + assert description == "Desc." + assert topics == [] + assert features == [] + + +def test_parse_model_output_trailing_blank_lines(): + output = 'Desc.\nTAGS: {"topics": ["games-fun"], "features": []}\n\n' + description, topics, features = write_docs.parse_model_output(output) + assert description == "Desc." + assert topics == ["games-fun"] + assert features == [] diff --git a/write_docs.py b/write_docs.py index 84b18857..de0f4f0a 100644 --- a/write_docs.py +++ b/write_docs.py @@ -2,12 +2,22 @@ # requires-python = ">=3.12" # /// -PROMPT = """ -Write or update a paragraph of documentation for this page as markdown. +import os +import json +import subprocess +import glob +import argparse +from pathlib import Path + +import tags_lib + +PROMPT_TEMPLATE = """ +Write or update documentation for this page, then tag it. + +First write a paragraph of documentation as markdown. Do not include any headings Do not use words like just or simply. Keep it to 2-3 sentences. -Return only the final description text, with no extra commentary. You may be given the full text of the previous description. Use that previous description as the starting point, updating it only when the current HTML shows @@ -16,16 +26,23 @@ Instead of starting with something like "This Bugzilla Bug Viewer is a web application for..." start with "View Mozilla Bugzilla bug reports..." or similar + +Then choose tags. Pick one or more "topic" tags describing what the tool does, +and zero or more "feature" tags naming the browser capabilities it actually uses +(read the HTML/JavaScript to confirm — do not guess at features that are not +present). Strongly prefer reusing an existing tag below; only coin a new +lower-case hyphenated slug when nothing existing fits. + +{vocabulary} + +Return exactly the description paragraph, then on its own final line: +TAGS: {{"topics": ["slug", ...], "features": ["slug", ...]}} +Return nothing else. """.strip() -import os -import subprocess -import glob -import re -import argparse -from pathlib import Path -COMMIT_MARKER_RE = re.compile(r"<!-- Generated from commit: ([a-f0-9]+) -->") +def build_system_prompt(): + return PROMPT_TEMPLATE.format(vocabulary=tags_lib.vocabulary_prompt_block()) def get_current_commit_hash(file_path): @@ -42,31 +59,60 @@ def get_current_commit_hash(file_path): return None -def extract_commit_hash_from_docs(docs_file_path): - """Extract the commit hash from a documentation file if it exists.""" +def read_docs(docs_file_path): + """Read a docs file's content, or return None if it does not exist.""" if not os.path.exists(docs_file_path): return None - with open(docs_file_path, "r", encoding="utf-8") as f: - content = f.read() + return f.read() - hash_match = COMMIT_MARKER_RE.search(content) - if hash_match: - return hash_match.group(1) - return None +def extract_commit_hash_from_docs(docs_file_path): + """Extract the commit hash from a documentation file if it exists.""" + content = read_docs(docs_file_path) + return tags_lib.extract_commit_hash(content) if content else None def extract_previous_description_from_docs(docs_file_path): - """Extract the existing generated description without the commit marker.""" - if not os.path.exists(docs_file_path): + """Extract the existing generated description without any comments.""" + content = read_docs(docs_file_path) + if not content: return None - - with open(docs_file_path, "r", encoding="utf-8") as f: - content = f.read() - - description = COMMIT_MARKER_RE.sub("", content).strip() - return description or None + return tags_lib.extract_description(content) or None + + +def docs_have_tags(docs_file_path): + """Return True if the docs file already has at least one topic tag.""" + content = read_docs(docs_file_path) + if not content: + return False + topics, _ = tags_lib.parse_tags(content) + return bool(topics) + + +def parse_model_output(output): + """Split model output into (description, topics, features). + + The model returns the description paragraph followed by a final + ``TAGS: {json}`` line. A missing or malformed TAGS line yields empty tags. + """ + topics, features = [], [] + lines = output.strip().splitlines() + description_lines = lines + for index in range(len(lines) - 1, -1, -1): + stripped = lines[index].strip() + if not stripped: + continue + if stripped.upper().startswith("TAGS:"): + try: + payload = json.loads(stripped[len("TAGS:") :].strip()) + topics = [str(t).strip() for t in payload.get("topics", []) if str(t).strip()] + features = [str(f).strip() for f in payload.get("features", []) if str(f).strip()] + except (ValueError, AttributeError): + pass + description_lines = lines[:index] + break + return "\n".join(description_lines).strip(), topics, features def build_llm_input(html_file_path, previous_description=None): @@ -101,20 +147,43 @@ def build_llm_input(html_file_path, previous_description=None): def generate_documentation(html_file_path, previous_description=None): - """Generate documentation for an HTML file using Claude.""" + """Generate documentation and tags for an HTML file using Claude. + + Returns ``(description, topics, features)`` or ``None`` on failure. + """ try: result = subprocess.run( - ["llm", "-m", "claude-haiku-4.5", "--system", PROMPT], + ["llm", "-m", "claude-haiku-4.5", "--system", build_system_prompt()], input=build_llm_input(html_file_path, previous_description), capture_output=True, text=True, check=True, ) - return result.stdout.strip() except subprocess.CalledProcessError as e: print(f"Error generating documentation for {html_file_path}: {e}") return None + description, topics, features = parse_model_output(result.stdout) + if not description: + return None + return description, topics, features + + +def merge_new_tags(topics, features): + """Add any newly coined tags to tags.json so the vocabulary persists.""" + vocab = tags_lib.load_vocabulary() + changed = False + for namespace, slugs in (("topics", topics), ("features", features)): + bucket = vocab.setdefault(namespace, {}) + for slug in slugs: + if slug not in bucket: + bucket[slug] = slug.replace("-", " ").title() + changed = True + if changed: + with tags_lib.TAGS_PATH.open("w", encoding="utf-8") as fp: + json.dump(vocab, fp, indent=2, ensure_ascii=False) + fp.write("\n") + def main(): parser = argparse.ArgumentParser( @@ -161,8 +230,9 @@ def main(): # Get the commit hash from the existing docs file (if it exists) existing_hash = extract_commit_hash_from_docs(docs_file) - # Check if documentation needs to be updated - if existing_hash == current_hash: + # Regenerate when the HTML changed, or when an up-to-date docs file is + # still missing its tags (so existing tools get backfilled over time). + if existing_hash == current_hash and docs_have_tags(docs_file): if args.verbose: print(f" Documentation is up to date for {html_file}") skipped_count += 1 @@ -178,14 +248,20 @@ def main(): print(f" Generating documentation for {html_file}") previous_description = extract_previous_description_from_docs(docs_file) - doc_content = generate_documentation(html_file, previous_description) - if not doc_content: + generated = generate_documentation(html_file, previous_description) + if not generated: print(f" Failed to generate documentation for {html_file}") skipped_count += 1 continue - # Add the commit hash marker - doc_content += f"\n\n<!-- Generated from commit: {current_hash} -->" + description, topics, features = generated + merge_new_tags(topics, features) + doc_content = tags_lib.render_docs( + description, + topics=topics, + features=features, + commit_hash=current_hash, + ) # Write the documentation to file with open(docs_file, "w", encoding="utf-8") as f: From 8325a870511c567cbd6e72061cf4151cc15016eb Mon Sep 17 00:00:00 2001 From: Jesse Vincent <jesse@fsck.com> Date: Fri, 5 Jun 2026 15:16:59 -0700 Subject: [PATCH 2/7] Backfill topic + feature tags for all 215 tools Classified every tool's docs.md with topic tags (what it does) and feature tags (browser capabilities used), drawn from the tags.json vocabulary. Added web-serial to the vocabulary. --- ai-adoption.docs.md | 4 +++- alt-text-extractor.docs.md | 4 +++- analytics.docs.md | 4 +++- animated-rainbow-border.docs.md | 3 ++- animated-word-cloud.docs.md | 4 +++- annotated-presentations.docs.md | 4 +++- apsw-query.docs.md | 4 +++- arena-animated.docs.md | 3 ++- ares.docs.md | 3 ++- aria-live-regions.docs.md | 3 ++- audio-spectrum.docs.md | 4 +++- avatar-web-component.docs.md | 4 +++- badge-drawer.docs.md | 4 +++- badge-repl.docs.md | 4 +++- base64-gzip-decoder.docs.md | 3 ++- bbox-cropper.docs.md | 4 +++- big-words.docs.md | 4 +++- blackened-cauliflower-and-turkish-style-stew.docs.md | 4 +++- blog-to-newsletter.docs.md | 4 +++- bluesky-faves.docs.md | 4 +++- bluesky-firehose.docs.md | 4 +++- bluesky-quote-finder.docs.md | 4 +++- bluesky-resolve.docs.md | 4 +++- bluesky-search.docs.md | 4 +++- bluesky-thread.docs.md | 4 +++- bluesky-timeline.docs.md | 4 +++- bookmarklets.docs.md | 4 +++- box-shadow.docs.md | 4 +++- broadcast-channel-chat.docs.md | 3 ++- bugzilla-bug.docs.md | 4 +++- bullish-bearish.docs.md | 4 +++- california-clock-change.docs.md | 3 ++- census-reporter-claude.docs.md | 4 +++- census-reporter-gemini.docs.md | 4 +++- chrome-prompt-playground.docs.md | 4 +++- claude-code-timeline.docs.md | 4 +++- claude-token-counter.docs.md | 4 +++- cleanup-claude-code-paste.docs.md | 4 +++- click-grid-to-expand.docs.md | 3 ++- clipboard-backup.docs.md | 4 +++- clipboard-viewer.docs.md | 4 +++- code-with-claude-2025.docs.md | 3 ++- codex-timeline.docs.md | 4 +++- compare-pdfs.docs.md | 4 +++- cooking-timer.docs.md | 4 +++- cors-fetch.docs.md | 4 +++- csp-allow.docs.md | 4 +++- css-text-wrapping.docs.md | 3 ++- csv-marker-map.docs.md | 4 +++- curly-emdash.docs.md | 3 ++- datasette-io-preview.docs.md | 4 +++- date-calculator.docs.md | 3 ++- deep-research-viewer.docs.md | 4 +++- devon-lanes.docs.md | 3 ++- dns.docs.md | 4 +++- dot.docs.md | 4 +++- emoji-identifier.docs.md | 4 +++- encrypt.docs.md | 4 +++- escape-entities.docs.md | 4 +++- event-planner.docs.md | 3 ++- exif.docs.md | 4 +++- extract-urls.docs.md | 4 +++- ffmpeg-crop.docs.md | 4 +++- flexbox-playground.docs.md | 3 ++- footnotes-experiment.docs.md | 3 ++- gemini-bbox.docs.md | 4 +++- gemini-chat.docs.md | 4 +++- gemini-flash-tts.docs.md | 4 +++- gemini-image-json.docs.md | 3 ++- gemini-mask.docs.md | 4 +++- gemini-prompt.docs.md | 4 +++- gif-dissector.docs.md | 4 +++- gif-optimizer.docs.md | 4 +++- github-account.docs.md | 4 +++- github-api-write.docs.md | 4 +++- github-graphiql.docs.md | 4 +++- github-issue-to-markdown.docs.md | 4 +++- github-ratelimit.docs.md | 4 +++- github-repo-size.docs.md | 4 +++- github-repo-stats.docs.md | 4 +++- gpt-4o-audio-player.docs.md | 4 +++- gradient-card.docs.md | 4 +++- grid-lanes-polyfill.docs.md | 3 ++- hacker-news-filtered.docs.md | 4 +++- hacker-news-histogram.docs.md | 4 +++- hacker-news-thread-export.docs.md | 4 +++- haiku.docs.md | 4 +++- hn-comments-for-user.docs.md | 4 +++- html-preview.docs.md | 4 +++- html-validation-demo.docs.md | 3 ++- huggingface-storage.docs.md | 4 +++- icon-editor.docs.md | 4 +++- iframe-api-explorer.docs.md | 4 +++- iframe-resize.docs.md | 3 ++- iframe-sandbox.docs.md | 3 ++- image-print.docs.md | 4 +++- image-resize-quality.docs.md | 4 +++- image-to-jpeg.docs.md | 4 +++- image-to-svg.docs.md | 4 +++- inat-sightings.docs.md | 4 +++- incomplete-json-printer.docs.md | 4 +++- is-it-a-bird.docs.md | 4 +++- jina-embeddings-image-token-calculator.docs.md | 4 +++- jina-reader.docs.md | 4 +++- json-diff.docs.md | 3 ++- json-schema-builder.docs.md | 4 +++- json-string-extractor.docs.md | 4 +++- json-to-markdown-transcript.docs.md | 4 +++- json-to-yaml.docs.md | 4 +++- justhtml.docs.md | 4 +++- keyboard-debug.docs.md | 3 ++- keyboard-filters.docs.md | 3 ++- lightning-timer.docs.md | 4 +++- link-extractor.docs.md | 4 +++- link-temp.docs.md | 3 ++- llm-lib.docs.md | 4 +++- lobsters-bookmarklet.docs.md | 4 +++- manyana.docs.md | 4 +++- markdown-copy-component.docs.md | 4 +++- markdown-math.docs.md | 4 +++- markdown-svg-renderer.docs.md | 4 +++- mask-visualizer.docs.md | 3 ++- mdn-timelines.docs.md | 4 +++- micropython.docs.md | 4 +++- microquickjs.docs.md | 4 +++- milliseconds.docs.md | 4 +++- minesweeper.docs.md | 3 ++- mobile-tables.docs.md | 4 +++- mp3-inspector.docs.md | 4 +++- nav-for-headings.docs.md | 3 ++- new-yorker-style.docs.md | 4 +++- nicar-2026.docs.md | 4 +++- notes-to-markdown.docs.md | 4 +++- numpy-pyodide-lab.docs.md | 4 +++- ocr.docs.md | 4 +++- octave-explainer.docs.md | 4 +++- omit-needless-words.docs.md | 4 +++- open-sauce-2025.docs.md | 4 +++- openai-audio-output.docs.md | 4 +++- openai-audio.docs.md | 4 +++- openai-webrtc.docs.md | 4 +++- openfreemap-demo.docs.md | 3 ++- passkeys.docs.md | 4 +++- paste-html-subset.docs.md | 4 +++- paste-rich-text.docs.md | 4 +++- pasted-file-editor.docs.md | 4 +++- percentage-recalculator.docs.md | 3 ++- pge-outages-hmb.docs.md | 4 +++- php-deserializer.docs.md | 4 +++- pipfile.docs.md | 4 +++- pomodoro.docs.md | 4 +++- pretext-explainer.docs.md | 4 +++- progress.docs.md | 3 ++- prompt-caching.docs.md | 4 +++- prompts-js.docs.md | 3 ++- pyodide-bar-chart.docs.md | 4 +++- pyodide-repl.docs.md | 4 +++- pypi-changelog.docs.md | 4 +++- python-comment-stripper.docs.md | 4 +++- python-vulnerability-lookup.docs.md | 4 +++- qr-code-generator.docs.md | 4 +++- qr.docs.md | 4 +++- query-string-stripper.docs.md | 4 +++- quickjs.docs.md | 4 +++- reading-time.docs.md | 3 ++- red-extractor.docs.md | 4 +++- redis-array.docs.md | 4 +++- render-claude-citations.docs.md | 3 ++- render-markdown.docs.md | 4 +++- rich-text-to-markdown.docs.md | 4 +++- rtf-to-html.docs.md | 4 +++- schema-dsl.docs.md | 3 ++- side-panel-dialog.docs.md | 3 ++- sloccount.docs.md | 4 +++- social-media-cropper.docs.md | 4 +++- software-heritage-repo.docs.md | 4 +++- sort-algorithms.docs.md | 3 ++- species-observation-map.docs.md | 4 +++- speech-synthesis.docs.md | 4 +++- sql-pretty-printer.docs.md | 4 +++- sqlite-ast.docs.md | 4 +++- sqlite-bytecode-explorer.docs.md | 4 +++- sqlite-qrf.docs.md | 4 +++- sqlite-wasm.docs.md | 4 +++- svg-progressive-render.docs.md | 4 +++- svg-render.docs.md | 4 +++- svg-sandbox.docs.md | 4 +++- swagger-subset.docs.md | 4 +++- syntaqlite.docs.md | 4 +++- tacopy-playground.docs.md | 4 +++- tags.json | 3 ++- terminal-to-html.docs.md | 4 +++- text-diff.docs.md | 3 ++- text-indentation.docs.md | 4 +++- text-wrap-balance-nav.docs.md | 3 ++- tiff-orientation.docs.md | 4 +++- timezones.docs.md | 4 +++- token-usage.docs.md | 3 ++- transfer-time.docs.md | 3 ++- transparent-png.docs.md | 4 +++- turbo-pascal-deconstructed.docs.md | 3 ++- unicode-binary-search.docs.md | 4 +++- unix-timestamp.docs.md | 3 ++- usborne-mad-house.docs.md | 3 ++- user-agent.docs.md | 3 ++- v86.docs.md | 4 +++- view-pdf.docs.md | 4 +++- visualizer.docs.md | 4 +++- webkitdirectory.docs.md | 4 +++- wikipedia-wikitext.docs.md | 4 +++- word-counter.docs.md | 4 +++- writing-style.docs.md | 3 ++- xml-validator.docs.md | 3 ++- yaml-explorer.docs.md | 4 +++- youtube-thumbnails.docs.md | 4 +++- zip-wheel-explorer.docs.md | 4 +++- 216 files changed, 600 insertions(+), 216 deletions(-) diff --git a/ai-adoption.docs.md b/ai-adoption.docs.md index 8577cd50..56d6455e 100644 --- a/ai-adoption.docs.md +++ b/ai-adoption.docs.md @@ -1,3 +1,5 @@ View AI adoption trends across different firm sizes by analyzing survey data on artificial intelligence usage in the workplace. This page runs a Python analysis using Pyodide to fetch employment survey data, calculate six-survey rolling averages, and generate an interactive visualization showing adoption rates by company size from November 2023 through August 2025. Download the resulting chart as PNG or SVG for further use or presentation. -<!-- Generated from commit: ecc4d0ed023901a9d26d99aea2b3bd34258e5241 --> \ No newline at end of file +<!-- topics: ai-llm, data-visualization --> +<!-- features: webassembly, fetch-network, canvas --> +<!-- Generated from commit: ecc4d0ed023901a9d26d99aea2b3bd34258e5241 --> diff --git a/alt-text-extractor.docs.md b/alt-text-extractor.docs.md index df7d1d04..bcce893d 100644 --- a/alt-text-extractor.docs.md +++ b/alt-text-extractor.docs.md @@ -1,3 +1,5 @@ Extract images and their associated metadata from pasted web content with this tool. When you paste rich text containing images, the application automatically retrieves each image's alt text, URL, and generates ready-to-use Markdown and HTML code snippets. Each extracted element can be individually copied to your clipboard for use in documentation, accessibility audits, or content management. -<!-- Generated from commit: 4f97126825cbfa22d001b5b81b6a4c4dd0e43094 --> \ No newline at end of file +<!-- topics: accessibility, text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: 4f97126825cbfa22d001b5b81b6a4c4dd0e43094 --> diff --git a/analytics.docs.md b/analytics.docs.md index 5a3b4cdd..58a51d54 100644 --- a/analytics.docs.md +++ b/analytics.docs.md @@ -2,4 +2,6 @@ Track your personal browsing activity across tools.simonwillison.net with real-time analytics stored locally in your browser. View detailed statistics including total visits, unique pages accessed, hourly and daily visit trends, top pages, and recent activity history. All data remains completely private—it is stored only in your browser's localStorage and is never transmitted to any server or shared with others. -<!-- Generated from commit: 36ac6466348fcb0d256f861d3b1e9d05c0facdc4 --> \ No newline at end of file +<!-- topics: productivity --> +<!-- features: local-storage, canvas, clipboard --> +<!-- Generated from commit: 36ac6466348fcb0d256f861d3b1e9d05c0facdc4 --> diff --git a/animated-rainbow-border.docs.md b/animated-rainbow-border.docs.md index d4bcff7e..ccce040b 100644 --- a/animated-rainbow-border.docs.md +++ b/animated-rainbow-border.docs.md @@ -1,3 +1,4 @@ Display an animated rainbow gradient border effect around a centered box with interactive controls. The page features a dark theme with a glowing, color-shifting border that can be toggled on and off using the provided button. The animation combines gradient shifting and pulsing effects to create a dynamic, eye-catching visual presentation. -<!-- Generated from commit: 99021c5a96c4d188e92a9341621a105e0d3600ca --> \ No newline at end of file +<!-- topics: css-layout, games-fun --> +<!-- Generated from commit: 99021c5a96c4d188e92a9341621a105e0d3600ca --> diff --git a/animated-word-cloud.docs.md b/animated-word-cloud.docs.md index 7a1c8f56..0b14d835 100644 --- a/animated-word-cloud.docs.md +++ b/animated-word-cloud.docs.md @@ -1,3 +1,5 @@ View animated word cloud visualizations that use an Archimedean spiral placement algorithm to position words on a canvas. Each word spirals outward from the center until it finds an unoccupied space, with grid-based spatial indexing accelerating collision detection to handle large datasets efficiently. Control the animation playback speed, step through frames manually, download the final result as a PNG, or paste your own text to generate a custom word cloud. -<!-- Generated from commit: 92c3a111e91f93397273845d2b76bb3cb59c3ca7 --> \ No newline at end of file +<!-- topics: data-visualization --> +<!-- features: canvas, url-state, fetch-network --> +<!-- Generated from commit: 92c3a111e91f93397273845d2b76bb3cb59c3ca7 --> diff --git a/annotated-presentations.docs.md b/annotated-presentations.docs.md index 3181447c..c93e9b3a 100644 --- a/annotated-presentations.docs.md +++ b/annotated-presentations.docs.md @@ -1,3 +1,5 @@ Create annotated presentation slides with alt text and markdown notes. Upload your slide images, add accessibility descriptions and annotations with markdown support, then generate HTML output using customizable templates. The tool automatically saves your work and includes optional OCR functionality to extract text from slides. -<!-- Generated from commit: 6c429482d2b7eb09c5e2554fe33c6157137f7bcc --> \ No newline at end of file +<!-- topics: documents-pdf, accessibility --> +<!-- features: file-upload, local-storage, webassembly --> +<!-- Generated from commit: 6c429482d2b7eb09c5e2554fe33c6157137f7bcc --> diff --git a/apsw-query.docs.md b/apsw-query.docs.md index 576b5bd3..1be7d42d 100644 --- a/apsw-query.docs.md +++ b/apsw-query.docs.md @@ -1,3 +1,5 @@ Analyze and explain SQLite queries using APSW by entering SQL code and executing it in an in-browser Python environment. The tool provides detailed query analysis including execution plans, expanded SQL, and query information to help understand how SQLite processes your queries. Optional setup SQL can be run before the main query to create tables or initialize data, and parameterized queries are supported through labeled input fields. -<!-- Generated from commit: 0af31729167e3de7f6ac73afd5e5bc03ba3b68fb --> \ No newline at end of file +<!-- topics: sqlite-databases, developer-tools --> +<!-- features: webassembly --> +<!-- Generated from commit: 0af31729167e3de7f6ac73afd5e5bc03ba3b68fb --> diff --git a/arena-animated.docs.md b/arena-animated.docs.md index c61714b9..763c6b5a 100644 --- a/arena-animated.docs.md +++ b/arena-animated.docs.md @@ -1,3 +1,4 @@ Compare Elo ratings across different language models and dates using this interactive animated bar chart. Load your own JSON data with model names, dates, and Elo scores, then watch the rankings evolve over time with customizable animation speed. The visualization displays the top 20 models at each time point, making it easy to track performance trends and competitive dynamics in the AI landscape. -<!-- Generated from commit: 9a2450df1bf8f426e243dc5f4964f0adc725de76 --> \ No newline at end of file +<!-- topics: ai-llm, data-visualization --> +<!-- Generated from commit: 9a2450df1bf8f426e243dc5f4964f0adc725de76 --> diff --git a/ares.docs.md b/ares.docs.md index 185ccc16..ac89a967 100644 --- a/ares.docs.md +++ b/ares.docs.md @@ -1,3 +1,4 @@ Convert text to NATO phonetic alphabet equivalents for clear communication in radio, military, and aviation contexts. Enter any combination of letters and numbers, then click the convert button to display the phonetic representation with each character separated by spaces. Spaces in the original text are marked as "(SPACE)" in the output. -<!-- Generated from commit: 9da6f96d4e3c886f1776cdc5b658e47087a279dd --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- Generated from commit: 9da6f96d4e3c886f1776cdc5b658e47087a279dd --> diff --git a/aria-live-regions.docs.md b/aria-live-regions.docs.md index 85edb174..325d0d92 100644 --- a/aria-live-regions.docs.md +++ b/aria-live-regions.docs.md @@ -1,3 +1,4 @@ Explore live region notifications with this interactive accessibility demo that allows you to test how screen readers announce dynamic content updates. The page provides instructions for testing with VoiceOver on macOS and iOS, plus interactive controls to trigger notifications with different aria-live settings (assertive or polite) to observe how screen readers prioritize and announce content changes. -<!-- Generated from commit: 30ad8d445379deeab726dc7d6c94a67e18de2f32 --> \ No newline at end of file +<!-- topics: accessibility, reference-education --> +<!-- Generated from commit: 30ad8d445379deeab726dc7d6c94a67e18de2f32 --> diff --git a/audio-spectrum.docs.md b/audio-spectrum.docs.md index 095a2c3c..7430488e 100644 --- a/audio-spectrum.docs.md +++ b/audio-spectrum.docs.md @@ -1,3 +1,5 @@ Visualize real-time audio frequency data from your microphone as an animated spectrum display. This application uses the Web Audio API to capture microphone input, analyze frequencies using FFT (Fast Fourier Transform), and render dynamic bars that respond to sound levels across the frequency spectrum. Grant microphone permissions when prompted to begin the visualization. -<!-- Generated from commit: 1390c401fa2e7a1797dba733a059390752a8a62a --> \ No newline at end of file +<!-- topics: audio-video, data-visualization --> +<!-- features: web-audio, canvas, camera-mic --> +<!-- Generated from commit: 1390c401fa2e7a1797dba733a059390752a8a62a --> diff --git a/avatar-web-component.docs.md b/avatar-web-component.docs.md index 46c92199..84a44672 100644 --- a/avatar-web-component.docs.md +++ b/avatar-web-component.docs.md @@ -1,3 +1,5 @@ Display and edit images with an interactive cropping interface for creating avatars or profile pictures. Users can select images by clicking, dragging and dropping files, or pasting from the clipboard, then crop them to a specified aspect ratio using resizable handles. The final cropped image is automatically exported as a JPEG data URL and can be synced to a designated form input field for seamless integration with web forms. -<!-- Generated from commit: 51b013005bea273913d5501fb6355c9aff93a97d --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, file-upload, drag-and-drop, clipboard --> +<!-- Generated from commit: 51b013005bea273913d5501fb6355c9aff93a97d --> diff --git a/badge-drawer.docs.md b/badge-drawer.docs.md index 1d0b2dc2..60be37f1 100644 --- a/badge-drawer.docs.md +++ b/badge-drawer.docs.md @@ -2,4 +2,6 @@ Draw pixel art for e-ink badge displays with this web-based canvas editor supporting multiple brush sizes, undo/redo functionality, and real-time black-and-white preview. Export your designs as PNG files or transfer them directly to Badger2040 devices running MicroPython via Web Serial. The editor maintains device-native resolution while offering adjustable zoom levels and includes features like grid overlay, background image loading, and URL-based bookmarking for saving your work. -<!-- Generated from commit: 914fd7c3e36f51e88c6674ffa2d9557f881c8072 --> \ No newline at end of file +<!-- topics: images-graphics, developer-tools --> +<!-- features: canvas, url-state, file-upload, web-serial --> +<!-- Generated from commit: 914fd7c3e36f51e88c6674ffa2d9557f881c8072 --> diff --git a/badge-repl.docs.md b/badge-repl.docs.md index f3de2832..9233729c 100644 --- a/badge-repl.docs.md +++ b/badge-repl.docs.md @@ -1,3 +1,5 @@ Interact with a MicroPython device via the Web Serial API to execute Python commands in real-time through a browser-based REPL interface. This tool enables direct communication with compatible microcontroller boards, allowing users to run Python code, query system information, and manage files without requiring terminal software or drivers. The interface provides quick-access buttons for common operations like listing files, checking CPU frequency, and monitoring available memory. -<!-- Generated from commit: 5cdacf6eb6ce834dd3814386e6860ec22af5fd5d --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: web-serial --> +<!-- Generated from commit: 5cdacf6eb6ce834dd3814386e6860ec22af5fd5d --> diff --git a/base64-gzip-decoder.docs.md b/base64-gzip-decoder.docs.md index 4d703217..7c25f302 100644 --- a/base64-gzip-decoder.docs.md +++ b/base64-gzip-decoder.docs.md @@ -1,3 +1,4 @@ Decode base64-encoded gzip data to retrieve the original decompressed content. Paste your base64 string into the input field and click the Decode button to process the data. The decoder handles the conversion from base64 format and gzip decompression in sequence, displaying the result or providing detailed error messages if the input is invalid. -<!-- Generated from commit: 2ef8cb4d03cd338b88ee72f8d811d839f311c525 --> \ No newline at end of file +<!-- topics: encoding-security, developer-tools --> +<!-- Generated from commit: 2ef8cb4d03cd338b88ee72f8d811d839f311c525 --> diff --git a/bbox-cropper.docs.md b/bbox-cropper.docs.md index d8678fd4..cc06dfb3 100644 --- a/bbox-cropper.docs.md +++ b/bbox-cropper.docs.md @@ -1,3 +1,5 @@ Draw bounding boxes on images using an interactive cropping tool powered by CropperJS. Load an image by pasting, dragging and dropping, or selecting a file, then click and drag to create a box around your region of interest. The tool automatically outputs normalized coordinates as percentages of the image dimensions in a format ready for command-line use. -<!-- Generated from commit: d117432950c0c71f304ef9c89da6c91a83883df4 --> \ No newline at end of file +<!-- topics: images-graphics, developer-tools --> +<!-- features: file-upload, drag-and-drop, clipboard --> +<!-- Generated from commit: d117432950c0c71f304ef9c89da6c91a83883df4 --> diff --git a/big-words.docs.md b/big-words.docs.md index c947690a..4bb44066 100644 --- a/big-words.docs.md +++ b/big-words.docs.md @@ -1,3 +1,5 @@ Display and customize large text with real-time formatting options including fonts, colors, gradients, and effects. Double-click or double-tap the display area to open the settings panel and adjust text content, styling, and background appearance. Share your creations by saving the customized URL with all your settings encoded as query parameters. -<!-- Generated from commit: 88649b855ef1043bb078fb1aaaa5b7c3df702c5a --> \ No newline at end of file +<!-- topics: text-writing, productivity --> +<!-- features: url-state --> +<!-- Generated from commit: 88649b855ef1043bb078fb1aaaa5b7c3df702c5a --> diff --git a/blackened-cauliflower-and-turkish-style-stew.docs.md b/blackened-cauliflower-and-turkish-style-stew.docs.md index b23a0fba..4fe58b96 100644 --- a/blackened-cauliflower-and-turkish-style-stew.docs.md +++ b/blackened-cauliflower-and-turkish-style-stew.docs.md @@ -2,4 +2,6 @@ Track and manage two simultaneous recipes with this interactive cooking timer that displays the current step, upcoming tasks, and a complete timeline with clock times. The timer persists across browser sessions, allowing you to pause and resume your cooking progress at any point. Color-coded tags distinguish between the Cauliflower & Couscous and Chickpea Stew recipes to help you stay organized while juggling multiple dishes. -<!-- Generated from commit: d26b2be2f78c1c2539b38bb9e5d8b1a9c6831a6c --> \ No newline at end of file +<!-- topics: productivity --> +<!-- features: local-storage --> +<!-- Generated from commit: d26b2be2f78c1c2539b38bb9e5d8b1a9c6831a6c --> diff --git a/blog-to-newsletter.docs.md b/blog-to-newsletter.docs.md index b33793af..28649056 100644 --- a/blog-to-newsletter.docs.md +++ b/blog-to-newsletter.docs.md @@ -2,4 +2,6 @@ This tool generates formatted HTML newsletter content from blog entries, links, quotes, and other content sourced from a Datasette backup of simonwillison.net. Users can customize the newsletter by filtering content from the past 1-60 days, optionally excluding items already featured in previous newsletters, and reordering blog entries through an intuitive drag-and-drop interface. The generated HTML can be copied directly into Substack, with additional features including sponsor message customization, URL length warnings for email compatibility, and integration with previous newsletter archives to prevent duplicate content. -<!-- Generated from commit: 75a1f212df34d91eb25249426318ab5cdb8d49e4 --> \ No newline at end of file +<!-- topics: productivity, text-writing --> +<!-- features: fetch-network, clipboard, local-storage, drag-and-drop --> +<!-- Generated from commit: 75a1f212df34d91eb25249426318ab5cdb8d49e4 --> diff --git a/bluesky-faves.docs.md b/bluesky-faves.docs.md index ca8118f8..4536a460 100644 --- a/bluesky-faves.docs.md +++ b/bluesky-faves.docs.md @@ -2,4 +2,6 @@ View liked posts from any Bluesky user by entering their profile URL, handle, or DID. This application fetches and displays a user's favorite posts with full post details including text, images, and engagement metrics, allowing you to browse and export the content in multiple formats. Simply enter a Bluesky profile identifier and the viewer will retrieve up to 200 of their most recent likes with the ability to load additional posts. -<!-- Generated from commit: 1eef44de4d0fd263637cda4aef562e49c976ad30 --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network, clipboard, url-state --> +<!-- Generated from commit: 1eef44de4d0fd263637cda4aef562e49c976ad30 --> diff --git a/bluesky-firehose.docs.md b/bluesky-firehose.docs.md index 8ebc7f45..d68e959e 100644 --- a/bluesky-firehose.docs.md +++ b/bluesky-firehose.docs.md @@ -1,3 +1,5 @@ Monitor real-time Bluesky feed data by connecting to the Bluesky Jetstream WebSocket service and viewing incoming posts and events. Send custom JSON messages to filter the feed by collection type, specific user DIDs, or other parameters, with all activity logged in the output panel for debugging and inspection. Use the provided keyboard shortcut (Ctrl/Cmd + Enter) to quickly send configuration updates to the WebSocket connection. -<!-- Generated from commit: 7c6af8eeabc7682b5f9ec2621e34bc771c5471d8 --> \ No newline at end of file +<!-- topics: social-feeds, developer-tools --> +<!-- features: websockets --> +<!-- Generated from commit: 7c6af8eeabc7682b5f9ec2621e34bc771c5471d8 --> diff --git a/bluesky-quote-finder.docs.md b/bluesky-quote-finder.docs.md index f4004246..f52901bc 100644 --- a/bluesky-quote-finder.docs.md +++ b/bluesky-quote-finder.docs.md @@ -1,3 +1,5 @@ Search for quote posts on Bluesky by entering a post URL to discover all responses that quote the original post. The tool fetches and displays these quotes with options to sort by likes, recency, or oldest first, and provides direct links to view each quote on Bluesky or explore its thread context. A color-coded depth indicator helps visualize the conversation hierarchy. -<!-- Generated from commit: d61f13e06cb664aee69fbe12c21a472f2c1a0daf --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: d61f13e06cb664aee69fbe12c21a472f2c1a0daf --> diff --git a/bluesky-resolve.docs.md b/bluesky-resolve.docs.md index e06b81b2..eefa2130 100644 --- a/bluesky-resolve.docs.md +++ b/bluesky-resolve.docs.md @@ -1,3 +1,5 @@ View and resolve Bluesky handles to their corresponding Decentralized Identifiers (DIDs) using the AT Protocol API. Enter a Bluesky handle in the format `username.bsky.social` to retrieve the associated DID, which serves as a unique identifier for accounts on the Bluesky network. This tool provides a simple interface for looking up handle-to-DID mappings through Bluesky's public resolver endpoint. -<!-- Generated from commit: 1472c5df0a4a8e97ee67543600403e642d504f0b --> \ No newline at end of file +<!-- topics: social-feeds, developer-tools --> +<!-- features: fetch-network --> +<!-- Generated from commit: 1472c5df0a4a8e97ee67543600403e642d504f0b --> diff --git a/bluesky-search.docs.md b/bluesky-search.docs.md index 1c8d4627..57314ade 100644 --- a/bluesky-search.docs.md +++ b/bluesky-search.docs.md @@ -1,3 +1,5 @@ Search Bluesky posts using advanced filters and options to organize results by latest or top engagement. This tool requires authentication with your Bluesky account credentials and supports filtering by date range, author, mentions, language, domain, URL, and hashtags. Results can be exported as formatted markdown for easy sharing and documentation. -<!-- Generated from commit: 86aaf4865dc096a40771889e2b6a8abf3fe97c0d --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network, clipboard, local-storage, url-state --> +<!-- Generated from commit: 86aaf4865dc096a40771889e2b6a8abf3fe97c0d --> diff --git a/bluesky-thread.docs.md b/bluesky-thread.docs.md index 4be9e7ef..879bd057 100644 --- a/bluesky-thread.docs.md +++ b/bluesky-thread.docs.md @@ -1,3 +1,5 @@ View Bluesky thread conversations with multiple display options including nested thread view, chronological sorting, and media support. This viewer fetches complete discussion threads from Bluesky posts and renders them with color-coded depth indicators, clickable reply relationships, and embedded images and videos. Users can switch between different viewing modes, copy thread text or raw JSON data, and optionally hide non-author replies to focus on the original poster's main conversation. -<!-- Generated from commit: e766dd32ea7be2d0ab72afaddfa7787cb690da77 --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network, clipboard, svg, url-state --> +<!-- Generated from commit: e766dd32ea7be2d0ab72afaddfa7787cb690da77 --> diff --git a/bluesky-timeline.docs.md b/bluesky-timeline.docs.md index 86377583..ba5484f7 100644 --- a/bluesky-timeline.docs.md +++ b/bluesky-timeline.docs.md @@ -1,3 +1,5 @@ View Bluesky social media timelines by authenticating with your account credentials and retrieving live feed data. The application automatically refreshes your timeline at regular intervals while displaying posts with author information, timestamps, and full JSON response data for advanced inspection. Credentials are securely stored locally in your browser for convenient access during future sessions. -<!-- Generated from commit: 7eff228bf303ad29a3ca006831ae7d5dae6201c1 --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network, local-storage --> +<!-- Generated from commit: 7eff228bf303ad29a3ca006831ae7d5dae6201c1 --> diff --git a/bookmarklets.docs.md b/bookmarklets.docs.md index 8efbf08f..ed0b8aa2 100644 --- a/bookmarklets.docs.md +++ b/bookmarklets.docs.md @@ -1,3 +1,5 @@ Access a collection of practical bookmarklets for web development and general browsing tasks. Each bookmarklet can be installed by dragging it to your bookmarks bar on desktop browsers or by copying the code for mobile Safari. The collection includes tools for revealing page anchor points and viewing page source code with formatting options, all presented with detailed documentation and source code inspection capabilities. -<!-- Generated from commit: 0804a5a97e69c724db4cab72661e5967730be7fe --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: clipboard --> +<!-- Generated from commit: 0804a5a97e69c724db4cab72661e5967730be7fe --> diff --git a/box-shadow.docs.md b/box-shadow.docs.md index 52046e2f..74ea2fd9 100644 --- a/box-shadow.docs.md +++ b/box-shadow.docs.md @@ -1,3 +1,5 @@ Generate custom CSS box-shadow effects with interactive controls and real-time preview. Adjust horizontal and vertical offsets, blur radius, spread radius, color, and opacity using intuitive sliders and color picker to visualize shadow changes instantly. Copy the generated CSS code directly to your clipboard for immediate use in your stylesheets. -<!-- Generated from commit: 44e0b09ad71ab22503ccf7edc0dbbec209bb2e05 --> \ No newline at end of file +<!-- topics: css-layout, developer-tools --> +<!-- features: clipboard --> +<!-- Generated from commit: 44e0b09ad71ab22503ccf7edc0dbbec209bb2e05 --> diff --git a/broadcast-channel-chat.docs.md b/broadcast-channel-chat.docs.md index 8fd9cac4..d710e21b 100644 --- a/broadcast-channel-chat.docs.md +++ b/broadcast-channel-chat.docs.md @@ -1,3 +1,4 @@ Send chat messages that synchronize instantly across multiple browser tabs using the Broadcast Channel API. Each tab displays messages sent from other tabs with a sync indicator, allowing real-time communication without requiring a backend server. Open multiple tabs of this page to see messages propagate automatically across all instances. -<!-- Generated from commit: 569bb9004a556ab797b3f6ba7ebe14f21b7514f6 --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- Generated from commit: 569bb9004a556ab797b3f6ba7ebe14f21b7514f6 --> diff --git a/bugzilla-bug.docs.md b/bugzilla-bug.docs.md index d975f49b..76b6a3fd 100644 --- a/bugzilla-bug.docs.md +++ b/bugzilla-bug.docs.md @@ -1,3 +1,5 @@ View Mozilla Bugzilla bug reports with a streamlined interface that displays bug details, comments, and change history in an organized timeline format. Enter a bug ID, URL, or Bugzilla link to retrieve comprehensive information including status, dependencies, keywords, and all activity related to the bug. The viewer automatically fetches and displays details about related bugs referenced in dependencies and history changes, making it easy to navigate connections between issues. -<!-- Generated from commit: 96d20a53f6df95e709fc2702450febf6619c99b2 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: 96d20a53f6df95e709fc2702450febf6619c99b2 --> diff --git a/bullish-bearish.docs.md b/bullish-bearish.docs.md index 2ae38031..96756dd7 100644 --- a/bullish-bearish.docs.md +++ b/bullish-bearish.docs.md @@ -1,3 +1,5 @@ Learn the difference between bullish and bearish market sentiment through an interactive visual guide featuring animated bull and bear characters. The page uses intuitive animal metaphors—bulls thrust their horns upward to represent rising markets and optimism, while bears swipe downward to represent falling markets and pessimism. A built-in quiz feature helps reinforce these concepts with randomized questions about market terminology. -<!-- Generated from commit: c80aaf0926ca27bc82be9ff782ad95323da04f3e --> \ No newline at end of file +<!-- topics: reference-education --> +<!-- features: svg --> +<!-- Generated from commit: c80aaf0926ca27bc82be9ff782ad95323da04f3e --> diff --git a/california-clock-change.docs.md b/california-clock-change.docs.md index 49a197ab..e0491dbd 100644 --- a/california-clock-change.docs.md +++ b/california-clock-change.docs.md @@ -1,3 +1,4 @@ Track California's Daylight Saving Time changes with this tool that displays the most recent clock adjustment and alerts you to the next one. The page automatically detects your timezone and restricts functionality to Pacific Time users, while offering detailed information about when clocks spring forward or fall back, along with a note about how the change might affect your dog's internal schedule. An embedded test suite verifies the accuracy of DST date calculations for multiple years. -<!-- Generated from commit: 181166fe79f697569e96f05e44f71d9a652146ff --> \ No newline at end of file +<!-- topics: productivity, reference-education --> +<!-- Generated from commit: 181166fe79f697569e96f05e44f71d9a652146ff --> diff --git a/census-reporter-claude.docs.md b/census-reporter-claude.docs.md index 41b93138..04c6b082 100644 --- a/census-reporter-claude.docs.md +++ b/census-reporter-claude.docs.md @@ -2,4 +2,6 @@ Explore American Community Survey demographic and social data through an interactive search and visualization tool. Select geographies such as cities, counties, or states alongside census topics like income, education, or housing to retrieve detailed population estimates with margin of error values. The application presents census data in both tabular and chart formats, making it easy to compare statistics across multiple locations and time periods using the Census Reporter API. -<!-- Generated from commit: 43c7b98b0a3d37adfe18a73021255739c98b11a8 --> \ No newline at end of file +<!-- topics: data-visualization, maps-geo --> +<!-- features: fetch-network, canvas --> +<!-- Generated from commit: 43c7b98b0a3d37adfe18a73021255739c98b11a8 --> diff --git a/census-reporter-gemini.docs.md b/census-reporter-gemini.docs.md index 5f4ade1f..a3256e56 100644 --- a/census-reporter-gemini.docs.md +++ b/census-reporter-gemini.docs.md @@ -2,4 +2,6 @@ Explore demographic and economic data from the US Census American Community Survey using the Census Reporter API. This tool allows you to search for specific geographic locations and data tables, then retrieve detailed census statistics including estimates and margins of error. Simply select a geography and one or more data tables to view comprehensive statistical breakdowns organized by column with their corresponding uncertainty measurements. -<!-- Generated from commit: d98b017f9a1c071f0d55e4f24d34313e36a7240c --> \ No newline at end of file +<!-- topics: data-visualization, maps-geo --> +<!-- features: fetch-network --> +<!-- Generated from commit: d98b017f9a1c071f0d55e4f24d34313e36a7240c --> diff --git a/chrome-prompt-playground.docs.md b/chrome-prompt-playground.docs.md index e2e49288..c4a2c276 100644 --- a/chrome-prompt-playground.docs.md +++ b/chrome-prompt-playground.docs.md @@ -1,3 +1,5 @@ Interact with Chrome's built-in language model API through this web-based playground interface. The application allows users to check model availability, download the model if needed, and execute text prompts to generate responses directly in the browser. A persistent history feature maintains records of previous prompts and responses for easy reference. -<!-- Generated from commit: 1ba6752f5d7d8a2e4146993231bfef4a92945f0c --> \ No newline at end of file +<!-- topics: ai-llm, developer-tools --> +<!-- features: local-storage --> +<!-- Generated from commit: 1ba6752f5d7d8a2e4146993231bfef4a92945f0c --> diff --git a/claude-code-timeline.docs.md b/claude-code-timeline.docs.md index 71d17799..2e200eb2 100644 --- a/claude-code-timeline.docs.md +++ b/claude-code-timeline.docs.md @@ -1,3 +1,5 @@ View Claude Code session `.jsonl` files as an interactive timeline with customizable filtering and search capabilities. This tool displays events chronologically, extracting conversation messages, tool calls, and file snapshots with formatted previews of text content, code blocks, and embedded images. Use the file picker, drag-and-drop, paste input, or URL fetch to load your session data and explore it with timezone switching, content-type filters, and easy JSON export. -<!-- Generated from commit: fdf7dab46adb9661766455cbf81a611969c6a778 --> \ No newline at end of file +<!-- topics: developer-tools, ai-llm --> +<!-- features: file-upload, drag-and-drop, fetch-network, clipboard, url-state --> +<!-- Generated from commit: fdf7dab46adb9661766455cbf81a611969c6a778 --> diff --git a/claude-token-counter.docs.md b/claude-token-counter.docs.md index 8f586869..7e948c57 100644 --- a/claude-token-counter.docs.md +++ b/claude-token-counter.docs.md @@ -1,3 +1,5 @@ Count tokens in text and images across multiple Claude models using Anthropic's token counting API. This tool allows you to compare token usage between different Claude models, helping you optimize costs and understand how system prompts and attachments affect token counts. Simply enter your content, select which models to compare, and the tool will display token counts alongside multipliers showing relative usage. -<!-- Generated from commit: 8533243d54be5b335d00075e3c7ff9f5c0bbcfe3 --> \ No newline at end of file +<!-- topics: ai-llm, developer-tools --> +<!-- features: fetch-network, file-upload, drag-and-drop --> +<!-- Generated from commit: 8533243d54be5b335d00075e3c7ff9f5c0bbcfe3 --> diff --git a/cleanup-claude-code-paste.docs.md b/cleanup-claude-code-paste.docs.md index 328e1912..ede443b2 100644 --- a/cleanup-claude-code-paste.docs.md +++ b/cleanup-claude-code-paste.docs.md @@ -1,3 +1,5 @@ Clean up Claude Code terminal output by removing the ❯ prompt character, fixing whitespace from line wrapping, and joining broken lines into readable paragraphs. Paste your terminal text into the input field and the cleaned output will appear automatically, ready to copy to your clipboard. -<!-- Generated from commit: 787cb39d44c9f2f881c731720633cf3788624370 --> \ No newline at end of file +<!-- topics: text-writing, ai-llm --> +<!-- features: clipboard --> +<!-- Generated from commit: 787cb39d44c9f2f881c731720633cf3788624370 --> diff --git a/click-grid-to-expand.docs.md b/click-grid-to-expand.docs.md index d776135a..1c237556 100644 --- a/click-grid-to-expand.docs.md +++ b/click-grid-to-expand.docs.md @@ -1,3 +1,4 @@ Explore an interactive CSS grid layout that demonstrates dynamic element expansion with smooth animations. Click the green cell labeled "1x2" to trigger a symmetric animation that expands the element to fill the entire grid container, then click again to animate it back to its original position. The layout combines CSS Grid positioning with JavaScript event handling to create a polished visual effect that smoothly transitions between states. -<!-- Generated from commit: 1faccef4c2390ded2dc2db0d0ff59bf3248d4c50 --> \ No newline at end of file +<!-- topics: css-layout, reference-education --> +<!-- Generated from commit: 1faccef4c2390ded2dc2db0d0ff59bf3248d4c50 --> diff --git a/clipboard-backup.docs.md b/clipboard-backup.docs.md index ad777105..235da905 100644 --- a/clipboard-backup.docs.md +++ b/clipboard-backup.docs.md @@ -1,3 +1,5 @@ Save and manage clipboard content across multiple formats including text, HTML, RTF, and images with this clipboard backup tool. Paste any content from your clipboard to automatically create a backup that can be restored later or downloaded in its original format. All backups are stored locally in your browser using IndexedDB, giving you persistent access to your clipboard history without any external uploads or server storage. -<!-- Generated from commit: 75818b81671d52258cbd268a7c3b34a8685b2726 --> \ No newline at end of file +<!-- topics: productivity, developer-tools --> +<!-- features: clipboard, indexeddb, canvas, file-upload --> +<!-- Generated from commit: 75818b81671d52258cbd268a7c3b34a8685b2726 --> diff --git a/clipboard-viewer.docs.md b/clipboard-viewer.docs.md index c5c95199..87151e80 100644 --- a/clipboard-viewer.docs.md +++ b/clipboard-viewer.docs.md @@ -1,3 +1,5 @@ Inspect and analyze clipboard data by pasting content into this viewer to see all available formats and their corresponding values. The tool displays text, HTML, images, and file information in an organized format, with special handling for image previews and multi-file pastes. This is useful for debugging clipboard operations and understanding what data formats are available when copying and pasting content across applications. -<!-- Generated from commit: 8397ef6722cd4120e7fe701b94a31b25aad960ab --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: clipboard --> +<!-- Generated from commit: 8397ef6722cd4120e7fe701b94a31b25aad960ab --> diff --git a/code-with-claude-2025.docs.md b/code-with-claude-2025.docs.md index 0c188e1e..1cf8cbc5 100644 --- a/code-with-claude-2025.docs.md +++ b/code-with-claude-2025.docs.md @@ -1,3 +1,4 @@ Download and view the complete conference schedule for May 22, 2025, in iCalendar format. This page provides access to all 25 events from the San Francisco conference, including keynotes, technical sessions, workshops, and office hours, which can be imported directly into your calendar application. A live preview of the ICS file contents is displayed below the download button for reference. -<!-- Generated from commit: 3b89dfb64d139d4ee5bdd2dbca7756e542ef6f21 --> \ No newline at end of file +<!-- topics: productivity --> +<!-- Generated from commit: 3b89dfb64d139d4ee5bdd2dbca7756e542ef6f21 --> diff --git a/codex-timeline.docs.md b/codex-timeline.docs.md index 8e907a33..fa2ee4f5 100644 --- a/codex-timeline.docs.md +++ b/codex-timeline.docs.md @@ -1,3 +1,5 @@ View Mozilla Codex rollout timeline events from `.jsonl` files with an interactive interface that supports filtering, searching, and detailed event inspection. Load files via drag-and-drop, paste, or URL fetch, then explore events organized chronologically with customizable timezone display and comprehensive event details including formatted content, tool calls, and reasoning blocks. -<!-- Generated from commit: 266b40cbefe398ec5a03b695f107cab7a5713529 --> \ No newline at end of file +<!-- topics: developer-tools, ai-llm --> +<!-- features: fetch-network, file-upload, drag-and-drop, clipboard, url-state --> +<!-- Generated from commit: 266b40cbefe398ec5a03b695f107cab7a5713529 --> diff --git a/compare-pdfs.docs.md b/compare-pdfs.docs.md index 1da2c8bb..bdf143ec 100644 --- a/compare-pdfs.docs.md +++ b/compare-pdfs.docs.md @@ -1,3 +1,5 @@ Compare two PDF documents side-by-side to identify differences between them. Upload or drag and drop two PDF files to view their pages rendered as images, with a third panel highlighting any pixel-level differences in red. This tool is useful for detecting changes between document versions, comparing drafts, or verifying document modifications. -<!-- Generated from commit: b3fcfe7df42e5fd896347c212f2b76283e047a78 --> \ No newline at end of file +<!-- topics: documents-pdf --> +<!-- features: file-upload, drag-and-drop, canvas --> +<!-- Generated from commit: b3fcfe7df42e5fd896347c212f2b76283e047a78 --> diff --git a/cooking-timer.docs.md b/cooking-timer.docs.md index 3c995a0c..f1848b2f 100644 --- a/cooking-timer.docs.md +++ b/cooking-timer.docs.md @@ -2,4 +2,6 @@ Create cooking recipes with detailed step-by-step instructions and automatically track elapsed time and upcoming tasks during meal preparation. Load recipes from URLs or paste JSON directly, save frequently-used recipes for quick access, and optionally cook multiple recipes simultaneously with synchronized timers. The application stores all state in your browser's local storage, allowing you to pause and resume cooking sessions at any time, and includes a QR code transfer feature for continuing your cooking session on a mobile device. -<!-- Generated from commit: 8188d00b333c40549f7b7fbe36f5a21077965ea5 --> \ No newline at end of file +<!-- topics: productivity --> +<!-- features: local-storage, canvas, fetch-network, url-state, clipboard --> +<!-- Generated from commit: 8188d00b333c40549f7b7fbe36f5a21077965ea5 --> diff --git a/cors-fetch.docs.md b/cors-fetch.docs.md index f999a5f4..a278fbd7 100644 --- a/cors-fetch.docs.md +++ b/cors-fetch.docs.md @@ -1,3 +1,5 @@ Test HTTP requests directly from your browser and observe which response headers and body content are accessible under CORS (Cross-Origin Resource Sharing) restrictions. This tool lets you construct requests with custom methods, headers, and body content, import requests from curl commands, and format JSON responses for easier inspection. The application preserves your request configuration in the URL fragment, allowing you to share and bookmark specific test cases. -<!-- Generated from commit: c32bcd73b70db5db6ef2fba5deba2b2d6e9807cb --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, url-state, clipboard --> +<!-- Generated from commit: c32bcd73b70db5db6ef2fba5deba2b2d6e9807cb --> diff --git a/csp-allow.docs.md b/csp-allow.docs.md index fe91ad47..22db5a2c 100644 --- a/csp-allow.docs.md +++ b/csp-allow.docs.md @@ -1,3 +1,5 @@ Experiment with Content Security Policy (CSP) allow-lists by editing HTML code in the left panel and observing how network requests are handled in the sandboxed preview on the right. Add trusted origins to the connect-src allow-list, and the application will prompt you to approve blocked requests from the sandbox, automatically updating your CSP configuration. This tool helps developers understand how CSP policies control resource loading and test dynamic allow-list management in real-time. -<!-- Generated from commit: 4dbfb23264757d118ca890c1d9f561ce4516ed4b --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- features: local-storage --> +<!-- Generated from commit: 4dbfb23264757d118ca890c1d9f561ce4516ed4b --> diff --git a/css-text-wrapping.docs.md b/css-text-wrapping.docs.md index 4109a834..d2b7de17 100644 --- a/css-text-wrapping.docs.md +++ b/css-text-wrapping.docs.md @@ -1,3 +1,4 @@ Learn how CSS text wrapping properties control how text flows within containers, including word-wrap, word-break, white-space, text-overflow, hyphens, line-break, and text-wrap. This guide provides interactive demonstrations of each property's behavior, detailed explanations of their values, and current browser compatibility information to help you choose the right approach for your text layout needs. -<!-- Generated from commit: bfc5f5ecc44a8d486379b2af746392692f1b4dc8 --> \ No newline at end of file +<!-- topics: css-layout, reference-education --> +<!-- Generated from commit: bfc5f5ecc44a8d486379b2af746392692f1b4dc8 --> diff --git a/csv-marker-map.docs.md b/csv-marker-map.docs.md index c4ddfa6e..f80d6166 100644 --- a/csv-marker-map.docs.md +++ b/csv-marker-map.docs.md @@ -1,3 +1,5 @@ View CSV data as markers on an interactive map using the `?csv=URL` parameter to specify a CSV file containing latitude and longitude columns. The map supports additional customization through query parameters including `center` to set the initial location, `zoom` for zoom level, `color` to change marker color, and `marker` to add individual points. Map position and zoom level are automatically saved to the URL bar as you navigate, allowing you to share your current view with others. -<!-- Generated from commit: 82fd5da0b9ce79c2dc7c42627e81f4e320e817f0 --> \ No newline at end of file +<!-- topics: maps-geo --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: 82fd5da0b9ce79c2dc7c42627e81f4e320e817f0 --> diff --git a/curly-emdash.docs.md b/curly-emdash.docs.md index d52e7b7c..5b8a0aa5 100644 --- a/curly-emdash.docs.md +++ b/curly-emdash.docs.md @@ -1,3 +1,4 @@ Identify curly quotes, curly apostrophes, and em dashes in your text with this highlighting tool. Paste or type content into the input panel to see matching characters highlighted in the preview, with real-time counts for each character type. This utility helps detect typographic characters that may have been introduced through word processors or web copy. -<!-- Generated from commit: 473a7e15e6c142be9ab4265dc39d5129ffab9ef8 --> \ No newline at end of file +<!-- topics: text-writing, developer-tools --> +<!-- Generated from commit: 473a7e15e6c142be9ab4265dc39d5129ffab9ef8 --> diff --git a/datasette-io-preview.docs.md b/datasette-io-preview.docs.md index ad2ed10f..71644271 100644 --- a/datasette-io-preview.docs.md +++ b/datasette-io-preview.docs.md @@ -1,3 +1,5 @@ Preview and validate datasette.io news entries in YAML format with real-time rendering and markdown linting. The editor loads the current news.yaml file from GitHub and provides immediate feedback on formatting errors, link validation, and markdown syntax issues while displaying a styled preview of how entries will appear on the live site. Use the error badge to track validation issues and fix them directly in the editor pane. -<!-- Generated from commit: 08ccddddf6305ed1f5853e6c4eb1da099ccf2394 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network --> +<!-- Generated from commit: 08ccddddf6305ed1f5853e6c4eb1da099ccf2394 --> diff --git a/date-calculator.docs.md b/date-calculator.docs.md index 3b8e93f5..ef126639 100644 --- a/date-calculator.docs.md +++ b/date-calculator.docs.md @@ -1,3 +1,4 @@ Calculate the time between two dates with detailed breakdowns and visual representations. This tool displays the total number of days, weeks, business days, and weekend days spanning your selected date range, along with a visual timeline showing where the dates fall relative to today. Use the calculation method options to focus on specific day types such as business days or weekends only. -<!-- Generated from commit: 37b5b99f1580921dae38424b9d5c34228775d66e --> \ No newline at end of file +<!-- topics: productivity --> +<!-- Generated from commit: 37b5b99f1580921dae38424b9d5c34228775d66e --> diff --git a/deep-research-viewer.docs.md b/deep-research-viewer.docs.md index 50cebdd8..171f943b 100644 --- a/deep-research-viewer.docs.md +++ b/deep-research-viewer.docs.md @@ -2,4 +2,6 @@ Analyze and visualize AI deep research transcripts with this interactive viewer that displays the complete research workflow including reasoning steps, web searches, visited pages, and code executions. Load transcripts from GitHub Gists, paste JSON directly, or view example data to explore how the AI model conducted research and arrived at its final conclusions. The viewer provides statistical summaries and a chronological timeline showing the model's thinking process, search queries, page visits, and computational steps in an easy-to-read format. -<!-- Generated from commit: a8bb00cc9d4d3c07e6d700283d7296593053e9a8 --> \ No newline at end of file +<!-- topics: ai-llm, developer-tools --> +<!-- features: fetch-network, file-upload, url-state --> +<!-- Generated from commit: a8bb00cc9d4d3c07e6d700283d7296593053e9a8 --> diff --git a/devon-lanes.docs.md b/devon-lanes.docs.md index 72606297..42db94c1 100644 --- a/devon-lanes.docs.md +++ b/devon-lanes.docs.md @@ -1,3 +1,4 @@ Navigate the treacherous single-track lanes of rural Devon in this interactive driving simulator, where you must manage your sanity while encountering cyclists, tractors, caravans, and other obstacles. Each encounter presents a unique challenge requiring a dice roll to succeed, with your choices affecting both your progress and mental state as you attempt to travel increasingly longer distances. The game combines humor, strategy, and unpredictable encounters to test whether you can survive the quirky chaos of England's countryside roads. -<!-- Generated from commit: 7312c5af1360c9f03e81d4eb621b9f08bf050f57 --> \ No newline at end of file +<!-- topics: games-fun --> +<!-- Generated from commit: 7312c5af1360c9f03e81d4eb621b9f08bf050f57 --> diff --git a/dns.docs.md b/dns.docs.md index 0f779a55..a577dbc5 100644 --- a/dns.docs.md +++ b/dns.docs.md @@ -2,4 +2,6 @@ Query DNS records for any domain using Cloudflare's DNS-over-HTTPS API with support for multiple record types (A, AAAA, CNAME, MX, NS, TXT, SOA, CAA, SRV, PTR) and three different resolvers. Choose between the standard 1.1.1.1 resolver, the malware-blocking 1.1.1.2, or the family-friendly 1.1.1.3 that filters both malware and adult content. Results display in an easy-to-read table format with TTL values, response flags, and status information, with an option to view raw JSON responses or query all record types at once. -<!-- Generated from commit: d473b6be87fd089c1c5fc81d40e12f68141a405b --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, clipboard, url-state --> +<!-- Generated from commit: d473b6be87fd089c1c5fc81d40e12f68141a405b --> diff --git a/dot.docs.md b/dot.docs.md index c0652f9e..f9e78f07 100644 --- a/dot.docs.md +++ b/dot.docs.md @@ -1,3 +1,5 @@ Render DOT graph files into visual diagrams directly in your browser. Paste your DOT syntax into the textarea and the graph will automatically render as an SVG visualization, with live updates as you edit. Share your graphs by copying the URL, which encodes your DOT content in the fragment identifier. -<!-- Generated from commit: a3fec50f7e8b7b0276fa19aca3f3bb61fb60130d --> \ No newline at end of file +<!-- topics: developer-tools, data-visualization --> +<!-- features: svg, url-state, webassembly --> +<!-- Generated from commit: a3fec50f7e8b7b0276fa19aca3f3bb61fb60130d --> diff --git a/emoji-identifier.docs.md b/emoji-identifier.docs.md index ef8d335e..d4a375b2 100644 --- a/emoji-identifier.docs.md +++ b/emoji-identifier.docs.md @@ -1,3 +1,5 @@ Extract and identify all emojis from text by pasting or typing into the input field, and instantly view their names and Unicode codepoint values. The tool uses a comprehensive emoji detection regex pattern combined with a Unicode emoji dataset to recognize a wide variety of emoji characters, including skin tone variants and zero-width joiner sequences. Results are displayed in real-time, showing each unique emoji found along with its standardized name and corresponding Unicode representation. -<!-- Generated from commit: 5072713dbebf789683182021f37c6b3f654008a4 --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- features: fetch-network --> +<!-- Generated from commit: 5072713dbebf789683182021f37c6b3f654008a4 --> diff --git a/encrypt.docs.md b/encrypt.docs.md index 75b522d6..fbf4bd1e 100644 --- a/encrypt.docs.md +++ b/encrypt.docs.md @@ -1,3 +1,5 @@ Encrypt and decrypt messages using a passphrase with this web application that leverages modern browser cryptography APIs. The tool generates a secure shareable link containing an encrypted message that can only be decrypted with the correct passphrase, making it useful for sending sensitive information. All encryption and decryption operations occur entirely in the browser, ensuring your data never leaves your device. -<!-- Generated from commit: b4e3e15127ef2e1f451ff5e3db42a85c277ae8ca --> \ No newline at end of file +<!-- topics: encoding-security --> +<!-- features: clipboard, url-state --> +<!-- Generated from commit: b4e3e15127ef2e1f451ff5e3db42a85c277ae8ca --> diff --git a/escape-entities.docs.md b/escape-entities.docs.md index 6cc1d137..a6f0af24 100644 --- a/escape-entities.docs.md +++ b/escape-entities.docs.md @@ -1,3 +1,5 @@ Convert between special characters and their HTML entity representations with this bidirectional encoding tool. Select between Escape mode to convert characters like `<`, `>`, `&`, and quotes into their corresponding HTML entities, or Unescape mode to decode HTML entities back into readable characters. The tool supports named entities, decimal numeric references, and hexadecimal numeric references, with real-time conversion displayed in the output field. -<!-- Generated from commit: d8fd1ad5e6048ea6e1f8df91fe531f13cbc6dd3f --> \ No newline at end of file +<!-- topics: developer-tools, encoding-security --> +<!-- features: clipboard --> +<!-- Generated from commit: d8fd1ad5e6048ea6e1f8df91fe531f13cbc6dd3f --> diff --git a/event-planner.docs.md b/event-planner.docs.md index 224fc78d..c574c926 100644 --- a/event-planner.docs.md +++ b/event-planner.docs.md @@ -1,3 +1,4 @@ Plan events with timezone-aware scheduling and countdown tracking. This application allows you to input event details including title, description, location, date, and time across different US timezones, then automatically calculates the time remaining until the event and generates a shareable Google Calendar link. The tool displays all event information in a formatted summary and provides a convenient way to add the event directly to your Google Calendar account. -<!-- Generated from commit: 1d19215d11b88842d1ee77ae6e81a4f908e76d8d --> \ No newline at end of file +<!-- topics: productivity --> +<!-- Generated from commit: 1d19215d11b88842d1ee77ae6e81a4f908e76d8d --> diff --git a/exif.docs.md b/exif.docs.md index 4c2c2fa0..77397342 100644 --- a/exif.docs.md +++ b/exif.docs.md @@ -1,3 +1,5 @@ Extract EXIF metadata and GPS coordinates from uploaded images using this viewer. Simply upload or drag-and-drop an image file to instantly display all embedded EXIF data, including GPS latitude and longitude if available. The tool supports common image formats such as JPEG, PNG, and HEIC. -<!-- Generated from commit: 646e64b51e917dc72a0f8d86232b016e785722aa --> \ No newline at end of file +<!-- topics: images-graphics, developer-tools --> +<!-- features: file-upload, drag-and-drop --> +<!-- Generated from commit: 646e64b51e917dc72a0f8d86232b016e785722aa --> diff --git a/extract-urls.docs.md b/extract-urls.docs.md index a0bfe30c..38b36320 100644 --- a/extract-urls.docs.md +++ b/extract-urls.docs.md @@ -1,3 +1,5 @@ Extract URLs from copied web page content by pasting HTML into the input area, which automatically identifies and displays all hyperlinks found in the pasted material. The tool filters for valid HTTP links and provides a consolidated list in the output textarea, making it easy to copy all extracted URLs to your clipboard with a single button click. -<!-- Generated from commit: 0f7fb49fd53d83ca1648b4db931c69acf9605529 --> \ No newline at end of file +<!-- topics: developer-tools, text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: 0f7fb49fd53d83ca1648b4db931c69acf9605529 --> diff --git a/ffmpeg-crop.docs.md b/ffmpeg-crop.docs.md index 5e8f9fca..344f620a 100644 --- a/ffmpeg-crop.docs.md +++ b/ffmpeg-crop.docs.md @@ -1,3 +1,5 @@ Generate FFmpeg crop commands by uploading a video file and interactively defining a crop area using a draggable overlay. The tool provides both standard and iPhone-compatible FFmpeg command formats that automatically update as you adjust the crop box dimensions and position. This eliminates the need to manually calculate crop parameters for video editing workflows. -<!-- Generated from commit: c86f2226030d4506d32d7d652231d0cd60f0c17b --> \ No newline at end of file +<!-- topics: audio-video, developer-tools --> +<!-- features: file-upload --> +<!-- Generated from commit: c86f2226030d4506d32d7d652231d0cd60f0c17b --> diff --git a/flexbox-playground.docs.md b/flexbox-playground.docs.md index 80d3dae2..8cafce40 100644 --- a/flexbox-playground.docs.md +++ b/flexbox-playground.docs.md @@ -1,3 +1,4 @@ Experiment with CSS Flexbox properties in real-time using this interactive playground. Adjust container properties like flex-direction, justify-content, and align-items while watching the layout change instantly, then select individual items to customize their flex-grow, flex-shrink, flex-basis, and alignment settings. The dynamically generated CSS code output shows the exact syntax needed to recreate your layout, making it an effective learning tool for mastering flexbox concepts. -<!-- Generated from commit: 77adc930a4d5b3a2e7965a78dcb0055de35a404c --> \ No newline at end of file +<!-- topics: css-layout, reference-education --> +<!-- Generated from commit: 77adc930a4d5b3a2e7965a78dcb0055de35a404c --> diff --git a/footnotes-experiment.docs.md b/footnotes-experiment.docs.md index d5feb539..30addf6f 100644 --- a/footnotes-experiment.docs.md +++ b/footnotes-experiment.docs.md @@ -2,4 +2,5 @@ Explore an interactive footnote system that enhances document reading by displaying footnote content in contextual popups when you hover over or click footnote references. The implementation uses semantic HTML with proper ARIA roles for accessibility, combined with CSS styling and JavaScript to position popups dynamically based on viewport constraints. This approach maintains traditional navigation between footnotes and their references while providing a modern, user-friendly experience that works across both desktop and mobile devices. -<!-- Generated from commit: 77c9ac04dc387a80b8af1b68b9633484f09e1e4b --> \ No newline at end of file +<!-- topics: reference-education, text-writing --> +<!-- Generated from commit: 77c9ac04dc387a80b8af1b68b9633484f09e1e4b --> diff --git a/gemini-bbox.docs.md b/gemini-bbox.docs.md index 0c8e69ca..ad2e1f75 100644 --- a/gemini-bbox.docs.md +++ b/gemini-bbox.docs.md @@ -1,3 +1,5 @@ Analyze images using the Google Gemini API and visualize detected objects as bounding boxes or points overlaid on the original image with coordinate grid lines. The tool supports multiple Gemini model versions and can extract either bounding box coordinates in normalized format or point locations with labels, displaying the results alongside a detailed visualization canvas. Store your API key locally for convenient access across multiple sessions. -<!-- Generated from commit: 36d731382a722df612088913dcc9e648118636b6 --> \ No newline at end of file +<!-- topics: ai-llm, images-graphics --> +<!-- features: fetch-network, canvas, file-upload, local-storage --> +<!-- Generated from commit: 36d731382a722df612088913dcc9e648118636b6 --> diff --git a/gemini-chat.docs.md b/gemini-chat.docs.md index 45efc4b4..8c8c910a 100644 --- a/gemini-chat.docs.md +++ b/gemini-chat.docs.md @@ -1,3 +1,5 @@ Chat with Google's Gemini AI models directly in your browser using this interactive chat application. Simply enter your Gemini API key (stored locally for convenience) and select from multiple available models including Gemini 2.5 Flash, Pro, and various other versions to power your conversations. The app displays real-time streaming responses, tracks API usage metrics, and measures response duration to help you monitor your interactions. -<!-- Generated from commit: 6432b3799baafcfbc4d8d9762d8b9b0bfe28c6f5 --> \ No newline at end of file +<!-- topics: ai-llm --> +<!-- features: fetch-network, local-storage --> +<!-- Generated from commit: 6432b3799baafcfbc4d8d9762d8b9b0bfe28c6f5 --> diff --git a/gemini-flash-tts.docs.md b/gemini-flash-tts.docs.md index 01fe8b63..68e1b467 100644 --- a/gemini-flash-tts.docs.md +++ b/gemini-flash-tts.docs.md @@ -1,3 +1,5 @@ Convert text to natural-sounding speech using Google's Gemini 3.1 Flash TTS model with support for both single-speaker and multi-speaker conversation modes. The tool allows you to customize voice selection, apply directorial tags like `[whisper]` and `[short pause]` for dynamic delivery, and download the generated audio as a WAV file. Requires a valid Gemini API key to function. -<!-- Generated from commit: efbc14d5777dd77a0bf963e272f3852cb588637a --> \ No newline at end of file +<!-- topics: ai-llm, audio-video --> +<!-- features: fetch-network --> +<!-- Generated from commit: efbc14d5777dd77a0bf963e272f3852cb588637a --> diff --git a/gemini-image-json.docs.md b/gemini-image-json.docs.md index f4c19fc7..5b3857f5 100644 --- a/gemini-image-json.docs.md +++ b/gemini-image-json.docs.md @@ -1,3 +1,4 @@ Parse and visualize JSON responses from the Google Gemini image generation API, extracting and displaying generated images, text content, and usage metadata in a formatted layout. The tool supports direct JSON input through paste or by loading example datasets, making it useful for testing and inspecting Gemini API outputs including model version information and token usage statistics. -<!-- Generated from commit: a9bff11d4559b0a89078e16d356b275e1dc3208c --> \ No newline at end of file +<!-- topics: ai-llm, data-json --> +<!-- Generated from commit: a9bff11d4559b0a89078e16d356b275e1dc3208c --> diff --git a/gemini-mask.docs.md b/gemini-mask.docs.md index 3b60ca2a..2950e832 100644 --- a/gemini-mask.docs.md +++ b/gemini-mask.docs.md @@ -1,3 +1,5 @@ Use the Gemini API to analyze images and generate segmentation masks with visual overlays. Upload an image and provide a prompt describing what you want to segment, then the application displays bounding boxes and mask visualizations directly on the image canvas. Token usage metrics are provided for each API call, and you can choose from various Gemini model versions including thinking and non-thinking variants. -<!-- Generated from commit: 6432b3799baafcfbc4d8d9762d8b9b0bfe28c6f5 --> \ No newline at end of file +<!-- topics: ai-llm, images-graphics --> +<!-- features: fetch-network, canvas, file-upload, local-storage --> +<!-- Generated from commit: 6432b3799baafcfbc4d8d9762d8b9b0bfe28c6f5 --> diff --git a/gemini-prompt.docs.md b/gemini-prompt.docs.md index 89578a94..8e2a9366 100644 --- a/gemini-prompt.docs.md +++ b/gemini-prompt.docs.md @@ -1,3 +1,5 @@ Generate responses from Google's Gemini API with support for system prompts, model selection, and streaming output. The interface stores your API key securely in local storage and maintains a history of system prompts for quick reuse. Markdown formatting is automatically rendered in the output area, and you can copy responses to your clipboard with a single click. -<!-- Generated from commit: 8ef8fd6737514504f0debeebc858fcde651fc7f5 --> \ No newline at end of file +<!-- topics: ai-llm --> +<!-- features: fetch-network, clipboard, local-storage --> +<!-- Generated from commit: 8ef8fd6737514504f0debeebc858fcde651fc7f5 --> diff --git a/gif-dissector.docs.md b/gif-dissector.docs.md index 84c0d873..b04fc0f6 100644 --- a/gif-dissector.docs.md +++ b/gif-dissector.docs.md @@ -1,3 +1,5 @@ Parse and visualize animated GIF files by extracting individual frames, timing data, color palettes, and detailed metadata. Upload a GIF file to instantly decompose it into its constituent frames with precise delay measurements, disposal methods, transparency information, and global color table analysis. The tool renders composited frames to show exactly how the animation appears, while providing comprehensive technical details about the image structure and properties. -<!-- Generated from commit: 8d36bfd6bedeb8fae0e829b140f4fef04216e0b6 --> \ No newline at end of file +<!-- topics: images-graphics, developer-tools --> +<!-- features: canvas, file-upload, drag-and-drop --> +<!-- Generated from commit: 8d36bfd6bedeb8fae0e829b140f4fef04216e0b6 --> diff --git a/gif-optimizer.docs.md b/gif-optimizer.docs.md index e33d71d9..9fc00fd5 100644 --- a/gif-optimizer.docs.md +++ b/gif-optimizer.docs.md @@ -1,3 +1,5 @@ Optimize animated GIF files using gifsicle compiled to WebAssembly, with all processing occurring directly in your browser without server uploads. The application offers preset optimization profiles ranging from lossless compression to aggressive lossy reduction, along with manual control over parameters like color palette size, scaling, and dithering methods. Each optimization generates a preview and displays the resulting file size reduction, allowing you to compare multiple compression strategies before downloading your preferred version. -<!-- Generated from commit: ea924805f14bc826ca3c51686613cd476ff02251 --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: webassembly, file-upload, drag-and-drop --> +<!-- Generated from commit: ea924805f14bc826ca3c51686613cd476ff02251 --> diff --git a/github-account.docs.md b/github-account.docs.md index f164ecb2..fa04695d 100644 --- a/github-account.docs.md +++ b/github-account.docs.md @@ -1,3 +1,5 @@ Look up GitHub user profiles and account information by username or numeric account ID. This tool fetches account details from the GitHub REST API, displaying information such as the user's name, login handle, account ID, creation date, and profile avatar. The application stores rate limit information locally to prevent repeated requests during API throttling periods. -<!-- Generated from commit: 8fe6f1d70bd695e2f8e1cc9458e0c77a39c470a9 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, local-storage, url-state --> +<!-- Generated from commit: 8fe6f1d70bd695e2f8e1cc9458e0c77a39c470a9 --> diff --git a/github-api-write.docs.md b/github-api-write.docs.md index f9e31f2b..2a2c9345 100644 --- a/github-api-write.docs.md +++ b/github-api-write.docs.md @@ -1,3 +1,5 @@ Upload files and images to GitHub repositories using the GitHub API. This tool accepts either text content or image files and commits them to a specified repository path with proper authentication via personal access tokens. The interface automatically adapts to show relevant input fields based on whether you're uploading text or an image file. -<!-- Generated from commit: 4b7902dd659f4a47a4f3e751198fa8b48b5c3514 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, file-upload --> +<!-- Generated from commit: 4b7902dd659f4a47a4f3e751198fa8b48b5c3514 --> diff --git a/github-graphiql.docs.md b/github-graphiql.docs.md index 523e27f7..1944b4b7 100644 --- a/github-graphiql.docs.md +++ b/github-graphiql.docs.md @@ -1,3 +1,5 @@ Explore GitHub's GraphQL API using an interactive query interface that requires authentication via a personal access token. Enter your GitHub token to connect and start writing, executing, and testing GraphQL queries against GitHub's data in real-time. The explorer provides syntax highlighting, query validation, and response inspection capabilities within an embedded GraphiQL environment. -<!-- Generated from commit: a877d8ffb396e42868a1a429b302b674fe100970 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, local-storage --> +<!-- Generated from commit: a877d8ffb396e42868a1a429b302b674fe100970 --> diff --git a/github-issue-to-markdown.docs.md b/github-issue-to-markdown.docs.md index 13ec0e5a..388dee81 100644 --- a/github-issue-to-markdown.docs.md +++ b/github-issue-to-markdown.docs.md @@ -2,4 +2,6 @@ Convert GitHub issues and pull requests to markdown format by providing their URL and an optional personal access token for private repositories. The tool automatically fetches the issue details, all comments, and expands any inline code references with their actual content from the repository. Your GitHub token is securely stored in your browser's local storage for convenient access on subsequent visits. -<!-- Generated from commit: 2a0a0c26db427db87f0aa937c96a7da01b8f8994 --> \ No newline at end of file +<!-- topics: developer-tools, text-writing --> +<!-- features: fetch-network, local-storage, clipboard --> +<!-- Generated from commit: 2a0a0c26db427db87f0aa937c96a7da01b8f8994 --> diff --git a/github-ratelimit.docs.md b/github-ratelimit.docs.md index 772a0382..5c660147 100644 --- a/github-ratelimit.docs.md +++ b/github-ratelimit.docs.md @@ -1,3 +1,5 @@ Monitor your GitHub API usage and remaining rate limits with this authentication-based checker. After authenticating with your GitHub account, the tool displays detailed information about your API quotas across different resource types, including remaining calls, reset times, and visual progress indicators. The interface shows critical warnings when your limits are running low, helping you manage your API consumption effectively. -<!-- Generated from commit: d6b0634ce65c95cd5d55061c1cfcb03778b33419 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, local-storage --> +<!-- Generated from commit: d6b0634ce65c95cd5d55061c1cfcb03778b33419 --> diff --git a/github-repo-size.docs.md b/github-repo-size.docs.md index 868546ac..cda2acad 100644 --- a/github-repo-size.docs.md +++ b/github-repo-size.docs.md @@ -1,3 +1,5 @@ Check the size of any GitHub repository by entering the owner and repository name or pasting a GitHub URL. The tool fetches repository data from the GitHub API and displays the total size in kilobytes, megabytes, or gigabytes depending on the repository's scale. Results are automatically saved to the browser URL, allowing you to share or revisit repository size checks. -<!-- Generated from commit: 24e094de34a2936a429e6fce8f6c736039c1d9c7 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: 24e094de34a2936a429e6fce8f6c736039c1d9c7 --> diff --git a/github-repo-stats.docs.md b/github-repo-stats.docs.md index 16ac8a3a..bb8063f0 100644 --- a/github-repo-stats.docs.md +++ b/github-repo-stats.docs.md @@ -1,3 +1,5 @@ View GitHub repository statistics including commit counts, contributor information, language breakdowns, and release details by entering a repository name or URL. This tool fetches data directly from the GitHub REST API in your browser, displaying comprehensive metrics such as stars, forks, branches, tags, and activity timestamps. Optionally authenticate with GitHub to increase your API rate limit from 60 to 5,000 requests per hour. -<!-- Generated from commit: 8d4ba6e137643813d6112e820cf2cbfe75317b90 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, local-storage, url-state --> +<!-- Generated from commit: 8d4ba6e137643813d6112e820cf2cbfe75317b90 --> diff --git a/gpt-4o-audio-player.docs.md b/gpt-4o-audio-player.docs.md index a0d14526..b603578c 100644 --- a/gpt-4o-audio-player.docs.md +++ b/gpt-4o-audio-player.docs.md @@ -1,3 +1,5 @@ Play audio responses generated by OpenAI's GPT-4 with audio preview model by providing a GitHub Gist URL containing the API response JSON. The player extracts base64-encoded WAV audio data from the Gist, converts it to playable format, and displays the associated transcript. You can listen to the audio directly in the browser or download it as a WAV file. -<!-- Generated from commit: 0f89a8f69b446e94487459505933e0fdef812f48 --> \ No newline at end of file +<!-- topics: audio-video, ai-llm --> +<!-- features: fetch-network --> +<!-- Generated from commit: 0f89a8f69b446e94487459505933e0fdef812f48 --> diff --git a/gradient-card.docs.md b/gradient-card.docs.md index c363f02e..c8260bd2 100644 --- a/gradient-card.docs.md +++ b/gradient-card.docs.md @@ -1,3 +1,5 @@ Generate customizable gradient images with multiple pattern overlays and effects. This tool provides controls for linear, radial, and conic gradients with adjustable colors, along with options for layering various patterns including noise, geometric shapes, and textures. Additional features include film grain, vignetting, and blend mode controls to fine-tune the visual appearance, with the ability to export the final result as a PNG image or save and restore settings as JSON. -<!-- Generated from commit: a82c351827696e32ca9a9230b309b325fe11d1f4 --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, clipboard --> +<!-- Generated from commit: a82c351827696e32ca9a9230b309b325fe11d1f4 --> diff --git a/grid-lanes-polyfill.docs.md b/grid-lanes-polyfill.docs.md index 7931f8de..e58f16a7 100644 --- a/grid-lanes-polyfill.docs.md +++ b/grid-lanes-polyfill.docs.md @@ -2,4 +2,5 @@ Explore the CSS Grid Lanes polyfill, which brings native masonry-style layout capabilities to all browsers through the `display: grid-lanes` property. The demonstration showcases six practical layout patterns including photo galleries, varying column widths, newspaper-style articles with spanning elements, explicit item placement, horizontal brick layouts, and mega menus. Each example includes the relevant CSS code and interactive previews that automatically detect native browser support or activate the polyfill as needed. -<!-- Generated from commit: 8ca341f1fa7f535682f4cf4271669c99ef0befbb --> \ No newline at end of file +<!-- topics: css-layout, reference-education --> +<!-- Generated from commit: 8ca341f1fa7f535682f4cf4271669c99ef0befbb --> diff --git a/hacker-news-filtered.docs.md b/hacker-news-filtered.docs.md index e44497a7..61d934e8 100644 --- a/hacker-news-filtered.docs.md +++ b/hacker-news-filtered.docs.md @@ -1,3 +1,5 @@ Browse the latest Hacker News stories with customizable content filtering to exclude topics of your choice. Enter comma-separated terms to filter out posts matching those keywords across titles, URLs, and descriptions, and click Refresh to load the newest stories or press Enter to re-filter the current feed. Your filter preferences are automatically saved in your browser for future visits. -<!-- Generated from commit: df23f5cfb527ecd623bd5b4c3a100644c3f74084 --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network, local-storage --> +<!-- Generated from commit: df23f5cfb527ecd623bd5b4c3a100644c3f74084 --> diff --git a/hacker-news-histogram.docs.md b/hacker-news-histogram.docs.md index c55bc5ad..86dd9a39 100644 --- a/hacker-news-histogram.docs.md +++ b/hacker-news-histogram.docs.md @@ -1,3 +1,5 @@ Analyze Hacker News stories by searching for multiple terms across a custom time range and visualize the results as an interactive histogram. The tool fetches monthly hit counts from the Hacker News API for each search term, displaying data in a color-coded bar chart, sortable table, and exportable JSON format. Click any bar to view the actual stories matching that term within that month's date range. -<!-- Generated from commit: 124ab7411ce7728c12385b09cd75bdbefc88c172 --> \ No newline at end of file +<!-- topics: social-feeds, data-visualization --> +<!-- features: fetch-network --> +<!-- Generated from commit: 124ab7411ce7728c12385b09cd75bdbefc88c172 --> diff --git a/hacker-news-thread-export.docs.md b/hacker-news-thread-export.docs.md index bd8677a5..1a66702b 100644 --- a/hacker-news-thread-export.docs.md +++ b/hacker-news-thread-export.docs.md @@ -1,3 +1,5 @@ Export Hacker News discussion threads in a formatted, hierarchical structure by providing a post ID or direct link to the thread. The tool fetches all comments from the specified post and organizes them with numbered paths that show the conversation structure, making it easy to read and copy the entire discussion for archival or sharing purposes. -<!-- Generated from commit: aa30eeebb9583ba36d2c3d9ac2794e70199385c5 --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network, clipboard --> +<!-- Generated from commit: aa30eeebb9583ba36d2c3d9ac2794e70199385c5 --> diff --git a/haiku.docs.md b/haiku.docs.md index 8db16b75..fce336e6 100644 --- a/haiku.docs.md +++ b/haiku.docs.md @@ -2,4 +2,6 @@ Capture images from your device's camera and generate haiku poetry inspired by what you photograph using Claude's vision capabilities. Press the camera button to take a photo, and the AI will compose an original haiku based on the image content. The app stores your Anthropic API key locally for convenience and supports switching between front and rear-facing cameras on devices with multiple camera options. -<!-- Generated from commit: 481983f6237a5ca690c49f6c4762306c15d762b5 --> \ No newline at end of file +<!-- topics: ai-llm, images-graphics --> +<!-- features: camera-mic, fetch-network, local-storage, canvas --> +<!-- Generated from commit: 481983f6237a5ca690c49f6c4762306c15d762b5 --> diff --git a/hn-comments-for-user.docs.md b/hn-comments-for-user.docs.md index 299712f1..b794fc5a 100644 --- a/hn-comments-for-user.docs.md +++ b/hn-comments-for-user.docs.md @@ -1,3 +1,5 @@ View Hacker News comments for any user by entering their handle to retrieve up to 1,000 of their most recent comments. The tool displays each comment with its date, the story title, links to both the comment and the thread, and the full comment text in an easily readable format. You can then copy all the results to your clipboard for further analysis or archiving. -<!-- Generated from commit: 18f0014bf86f1f7fd6e20862cd8c1e77e7583021 --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network, clipboard --> +<!-- Generated from commit: 18f0014bf86f1f7fd6e20862cd8c1e77e7583021 --> diff --git a/html-preview.docs.md b/html-preview.docs.md index e5c942d1..959d720d 100644 --- a/html-preview.docs.md +++ b/html-preview.docs.md @@ -1,3 +1,5 @@ Write HTML code directly in the editor pane and see the rendered output update in real-time in the preview pane. The editor supports live preview with debounced updates to prevent excessive rendering, and includes a copy button to save your HTML code to the clipboard. On mobile devices, toggle between the editor and preview views using the dedicated button in the toolbar. -<!-- Generated from commit: a418a01e7b7aeae97b6992d21d1f93c04bacd8b8 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: clipboard --> +<!-- Generated from commit: a418a01e7b7aeae97b6992d21d1f93c04bacd8b8 --> diff --git a/html-validation-demo.docs.md b/html-validation-demo.docs.md index 14aa3262..43dbfd6d 100644 --- a/html-validation-demo.docs.md +++ b/html-validation-demo.docs.md @@ -1,3 +1,4 @@ Submit contact information through this responsive form that provides real-time validation using native HTML5 attributes and CSS-only feedback. The form validates required fields including name, email, and message content, displaying checkmarks for valid inputs and error messages for invalid entries without requiring any JavaScript. The clean, modern design features a card layout with smooth transitions and a collapsible source code viewer for examining the underlying HTML and CSS implementation. -<!-- Generated from commit: 42812c4ffde78c6385f7f96d664450fbf702bcf1 --> \ No newline at end of file +<!-- topics: reference-education, css-layout --> +<!-- Generated from commit: 42812c4ffde78c6385f7f96d664450fbf702bcf1 --> diff --git a/huggingface-storage.docs.md b/huggingface-storage.docs.md index 085376ce..d84d704c 100644 --- a/huggingface-storage.docs.md +++ b/huggingface-storage.docs.md @@ -1,3 +1,5 @@ Check the storage size of Hugging Face machine learning models by entering a model URL or repository path. The tool queries the Hugging Face API to retrieve the total storage used by the specified model and displays the result in a human-readable format (MB or GB). Models can be looked up using either their full Hugging Face URL or their model identifier in the format `username/model-name`. -<!-- Generated from commit: ab388dda297c98a8de2e111486fa2450f96fdf84 --> \ No newline at end of file +<!-- topics: ai-llm, developer-tools --> +<!-- features: fetch-network --> +<!-- Generated from commit: ab388dda297c98a8de2e111486fa2450f96fdf84 --> diff --git a/icon-editor.docs.md b/icon-editor.docs.md index e0f47747..3fa9b2f7 100644 --- a/icon-editor.docs.md +++ b/icon-editor.docs.md @@ -2,4 +2,6 @@ Create and edit 24×24 pixel icons with an intuitive browser-based editor featuring a live grid canvas, color picker, and emoji starter templates. Design your icons by clicking pixels directly on the canvas, customize colors using the preset palette or custom hex input, and optionally start with common emojis or custom characters that are automatically converted to pixelated artwork. Your work is automatically saved to the URL, allowing you to bookmark or share your designs without any backend storage requirements, and you can download your finished icon as a PNG file when complete. -<!-- Generated from commit: a1cf1d21cac6f68bb6ae12fda7430cfd21a6d043 --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, url-state --> +<!-- Generated from commit: a1cf1d21cac6f68bb6ae12fda7430cfd21a6d043 --> diff --git a/iframe-api-explorer.docs.md b/iframe-api-explorer.docs.md index 09a0321a..e5981a9f 100644 --- a/iframe-api-explorer.docs.md +++ b/iframe-api-explorer.docs.md @@ -2,4 +2,6 @@ Explore API endpoints and view their responses in real-time using this interactive tool. The interface uses sandboxed iframes with postMessage communication to safely fetch and display JSON data from remote APIs. Enter any API URL and submit to see the formatted response displayed directly in the browser. -<!-- Generated from commit: 3011fee9362b436d1b87a9dd2714dd429fafd245 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network --> +<!-- Generated from commit: 3011fee9362b436d1b87a9dd2714dd429fafd245 --> diff --git a/iframe-resize.docs.md b/iframe-resize.docs.md index 83841d97..9cedc55a 100644 --- a/iframe-resize.docs.md +++ b/iframe-resize.docs.md @@ -1,3 +1,4 @@ Embed untrusted content safely within a webpage using a sandboxed iframe that automatically adjusts its height without allowing cross-origin access. The prototype uses `postMessage` to communicate height changes between the sandboxed iframe and parent page, enabling seamless content display while maintaining security restrictions. Various content examples demonstrate how the sandbox handles dynamic content, images, and attempts at malicious behavior. -<!-- Generated from commit: 6e88344d337ee402c4fe06390fe5f8ce69be81ed --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- Generated from commit: 6e88344d337ee402c4fe06390fe5f8ce69be81ed --> diff --git a/iframe-sandbox.docs.md b/iframe-sandbox.docs.md index b9d4c57f..bae09ccf 100644 --- a/iframe-sandbox.docs.md +++ b/iframe-sandbox.docs.md @@ -1,3 +1,4 @@ Test and explore HTML, CSS, and JavaScript code in a sandboxed iframe environment with configurable security restrictions. The left panel provides a code editor for writing HTML content, while the right panel displays a live preview with customizable sandbox attributes that control what the iframe can access and execute. Use the checkboxes to enable or disable specific permissions like scripts, forms, popups, and same-origin access to understand how sandbox restrictions affect web content behavior. -<!-- Generated from commit: e62bd12ff34fdeb7a906f9b34303c17ea63d3a41 --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- Generated from commit: e62bd12ff34fdeb7a906f9b34303c17ea63d3a41 --> diff --git a/image-print.docs.md b/image-print.docs.md index 2e338429..f2ae76d5 100644 --- a/image-print.docs.md +++ b/image-print.docs.md @@ -1,3 +1,5 @@ Create custom photo print layouts for A4 pages with adjustable grid configurations, image fitting options, and portrait or landscape orientations. Users can add photos by uploading files or dragging and dropping them directly onto the page, then remove individual photos or clear the entire layout before printing. The preview displays actual print dimensions, allowing precise control over how photos will appear on the final printed output. -<!-- Generated from commit: f389301cb51c22552db22cac5e8d46b9f8e99cde --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: file-upload, drag-and-drop --> +<!-- Generated from commit: f389301cb51c22552db22cac5e8d46b9f8e99cde --> diff --git a/image-resize-quality.docs.md b/image-resize-quality.docs.md index 11b96a3e..957745f7 100644 --- a/image-resize-quality.docs.md +++ b/image-resize-quality.docs.md @@ -1,3 +1,5 @@ Compare images at different sizes and quality levels by uploading a photo, defining a crop area, and generating multiple preview versions with varying dimensions and compression settings. The tool displays file sizes for each variant and allows interactive toggling between normal and full-width viewing modes, as well as direct downloads. Transparency detection automatically reveals a background color picker when needed for images with alpha channels. -<!-- Generated from commit: 27b229c3898652cf7925ee9fe7222105a6fca707 --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, file-upload, drag-and-drop --> +<!-- Generated from commit: 27b229c3898652cf7925ee9fe7222105a6fca707 --> diff --git a/image-to-jpeg.docs.md b/image-to-jpeg.docs.md index b77b15c2..965bd2a3 100644 --- a/image-to-jpeg.docs.md +++ b/image-to-jpeg.docs.md @@ -1,3 +1,5 @@ Compress and optimize image files by uploading them to this web-based tool that applies adjustable JPEG quality settings to reduce file size. The interface allows users to compare the original and optimized versions side-by-side by toggling between views or pressing and holding the image, while providing real-time compression statistics and the ability to download the optimized file or copy its data URI for embedding in code. -<!-- Generated from commit: c080cb104f486599f020d49da5136331279f38fa --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, file-upload, drag-and-drop, clipboard --> +<!-- Generated from commit: c080cb104f486599f020d49da5136331279f38fa --> diff --git a/image-to-svg.docs.md b/image-to-svg.docs.md index 67d98fc7..c75be3da 100644 --- a/image-to-svg.docs.md +++ b/image-to-svg.docs.md @@ -1,3 +1,5 @@ Convert raster images to scalable vector graphics using automated tracing technology. Upload a JPG or PNG image by dragging it onto the drop zone or clicking to browse, and the application will generate an SVG representation that can be viewed and copied. The conversion process uses imagetracerjs to intelligently trace image edges and create vector paths suitable for scaling to any size without quality loss. -<!-- Generated from commit: 4ff37f2dfd5d0b5d63e9214fe44c820c471d5a56 --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, file-upload, drag-and-drop, clipboard --> +<!-- Generated from commit: 4ff37f2dfd5d0b5d63e9214fe44c820c471d5a56 --> diff --git a/inat-sightings.docs.md b/inat-sightings.docs.md index 04f9e7c8..d532c4b9 100644 --- a/inat-sightings.docs.md +++ b/inat-sightings.docs.md @@ -2,4 +2,6 @@ Browse iNaturalist species observations organized by sighting date and time. The page fetches data from a remote source and displays each clump of observations with associated photos, species names, and links to view full details on iNaturalist. Observations are presented in reverse chronological order, with thumbnails that expand to full-size images when clicked. -<!-- Generated from commit: f645e97d7d139b7357150d8cbafe0b9370f29de6 --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: fetch-network --> +<!-- Generated from commit: f645e97d7d139b7357150d8cbafe0b9370f29de6 --> diff --git a/incomplete-json-printer.docs.md b/incomplete-json-printer.docs.md index fd6e1815..8124faaf 100644 --- a/incomplete-json-printer.docs.md +++ b/incomplete-json-printer.docs.md @@ -1,3 +1,5 @@ Format truncated or incomplete JSON into readable structures with automatic live formatting as you type. This tool applies consistent indentation and proper spacing to malformed or partial JSON snippets, and displays validation status while the formatted output can be copied to the clipboard. Example data is available to test the functionality. -<!-- Generated from commit: 390a83ad24b691c897b16de5565fecbf9c63c8cc --> \ No newline at end of file +<!-- topics: data-json, developer-tools --> +<!-- features: clipboard --> +<!-- Generated from commit: 390a83ad24b691c897b16de5565fecbf9c63c8cc --> diff --git a/is-it-a-bird.docs.md b/is-it-a-bird.docs.md index 2cc6f88e..fc9a8e66 100644 --- a/is-it-a-bird.docs.md +++ b/is-it-a-bird.docs.md @@ -1,3 +1,5 @@ Determine whether images contain birds using OpenAI's CLIP model running directly in your browser through Transformers.js. Upload images by dragging and dropping, pasting from your clipboard, or selecting files, or use your device's camera for real-time analysis. The tool processes all images locally with no data sent to external servers, and includes a webcam mode with pinch-to-zoom functionality for mobile devices. -<!-- Generated from commit: 5eed328d7e2c2a0ce9554c4cfdf26999a0fd6fa7 --> \ No newline at end of file +<!-- topics: ai-llm, images-graphics --> +<!-- features: webassembly, camera-mic, file-upload, drag-and-drop --> +<!-- Generated from commit: 5eed328d7e2c2a0ce9554c4cfdf26999a0fd6fa7 --> diff --git a/jina-embeddings-image-token-calculator.docs.md b/jina-embeddings-image-token-calculator.docs.md index a809f142..98555801 100644 --- a/jina-embeddings-image-token-calculator.docs.md +++ b/jina-embeddings-image-token-calculator.docs.md @@ -1,3 +1,5 @@ Calculate the token cost for images used in API requests by uploading or dragging an image file into the tool. The calculator analyzes the image dimensions and divides them into 224-pixel tiles, multiplying the total tile count by 1,000 to determine the token expense. This helps estimate costs when working with vision-based APIs that charge per image token. -<!-- Generated from commit: 8ad34e5e2ac8f07b4e59a06c9f5dc9e874930268 --> \ No newline at end of file +<!-- topics: ai-llm --> +<!-- features: file-upload, drag-and-drop --> +<!-- Generated from commit: 8ad34e5e2ac8f07b4e59a06c9f5dc9e874930268 --> diff --git a/jina-reader.docs.md b/jina-reader.docs.md index d188e978..8ca3c068 100644 --- a/jina-reader.docs.md +++ b/jina-reader.docs.md @@ -1,3 +1,5 @@ Convert web pages to structured content using the Jina Reader API, with support for multiple output formats including markdown, HTML, and text. The interface allows you to fetch and preview page content while optionally running AI-powered analysis through Claude to generate summaries, extract quotes, and identify key ideas from the retrieved material. -<!-- Generated from commit: 0e83c1a01b476b112d05f3d57972c31907b21bdc --> \ No newline at end of file +<!-- topics: ai-llm, developer-tools --> +<!-- features: fetch-network, local-storage, clipboard --> +<!-- Generated from commit: 0e83c1a01b476b112d05f3d57972c31907b21bdc --> diff --git a/json-diff.docs.md b/json-diff.docs.md index c3e6fd80..d327f991 100644 --- a/json-diff.docs.md +++ b/json-diff.docs.md @@ -1,3 +1,4 @@ Compare JSON documents side-by-side to identify additions, removals, and modifications between two versions. The tool displays differences with color-coded highlighting and provides character-level detail for string changes, making it easy to spot exactly what has changed. Preloaded examples are available to explore common use cases like configuration updates, user profile changes, and API response comparisons. -<!-- Generated from commit: f98c630bbb2b7e1004a0a184274d88c3f9ab86df --> \ No newline at end of file +<!-- topics: data-json, developer-tools --> +<!-- Generated from commit: f98c630bbb2b7e1004a0a184274d88c3f9ab86df --> diff --git a/json-schema-builder.docs.md b/json-schema-builder.docs.md index c2ccb19e..fd75f044 100644 --- a/json-schema-builder.docs.md +++ b/json-schema-builder.docs.md @@ -1,3 +1,5 @@ Create JSON schemas interactively with this builder tool that allows you to define properties, set data types, and configure nested objects through an intuitive form interface. The generated schema is displayed in real-time and can be copied to your clipboard for use in your applications. Your schema is automatically saved in the URL, making it easy to share or revisit your work later. -<!-- Generated from commit: 0a186e5a3a939fc9e9679ecc31068494c1368b99 --> \ No newline at end of file +<!-- topics: data-json, developer-tools --> +<!-- features: clipboard, url-state --> +<!-- Generated from commit: 0a186e5a3a939fc9e9679ecc31068494c1368b99 --> diff --git a/json-string-extractor.docs.md b/json-string-extractor.docs.md index 5188592a..361df895 100644 --- a/json-string-extractor.docs.md +++ b/json-string-extractor.docs.md @@ -1,3 +1,5 @@ Extract all strings from JSON data that exceed 20 characters in length or contain line breaks. This tool is useful for identifying longer text content within complex JSON structures for review, localization, or documentation purposes. Simply paste JSON into the textarea to automatically display matching strings along with their object paths, and use the copy button to quickly transfer any string to your clipboard. -<!-- Generated from commit: 6fbfc694190f24e8c08abfd816cdf64edf42f3a1 --> \ No newline at end of file +<!-- topics: data-json, developer-tools --> +<!-- features: clipboard, fetch-network, url-state --> +<!-- Generated from commit: 6fbfc694190f24e8c08abfd816cdf64edf42f3a1 --> diff --git a/json-to-markdown-transcript.docs.md b/json-to-markdown-transcript.docs.md index 3ba61d2b..c4876e3d 100644 --- a/json-to-markdown-transcript.docs.md +++ b/json-to-markdown-transcript.docs.md @@ -1,3 +1,5 @@ Convert JSON transcripts from audio into formatted Markdown with speaker names and timestamps. This tool automatically processes JSON data containing speaker names, text, and timestamp information, formatting them into readable Markdown output that can be easily copied and pasted elsewhere. The tool includes instructions for generating the required JSON format using the LLM command-line tool with audio files. -<!-- Generated from commit: a1be73bf7de8175342f38bcbe7840c6f425ceae4 --> \ No newline at end of file +<!-- topics: data-json, text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: a1be73bf7de8175342f38bcbe7840c6f425ceae4 --> diff --git a/json-to-yaml.docs.md b/json-to-yaml.docs.md index 894f238e..638e2eb9 100644 --- a/json-to-yaml.docs.md +++ b/json-to-yaml.docs.md @@ -1,3 +1,5 @@ Convert JSON data into multiple YAML formats with a single paste. The tool generates three output variations—block style for readability, flow style for compactness, and quoted strings style for explicit formatting—allowing you to choose the best format for your needs. Each output can be copied to your clipboard with a single click. -<!-- Generated from commit: 5426b541ed61cf6a9d0b74c3acce637ca60a825a --> \ No newline at end of file +<!-- topics: data-json --> +<!-- features: clipboard --> +<!-- Generated from commit: 5426b541ed61cf6a9d0b74c3acce637ca60a825a --> diff --git a/justhtml.docs.md b/justhtml.docs.md index 6d7dceb4..db1e8ae5 100644 --- a/justhtml.docs.md +++ b/justhtml.docs.md @@ -1,3 +1,5 @@ Test the JustHTML Python HTML5 parser directly in your browser with this interactive playground. Parse, query, and manipulate HTML using CSS selectors, pretty-print documents, extract text content, and convert HTML to Markdown—all running client-side with Pyodide. The playground supports multiple analysis modes including tree structure visualization and streaming event inspection for comprehensive HTML document exploration. -<!-- Generated from commit: 172cd5ab9919eda995b8162c87b84bea7d58fb3a --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: webassembly, fetch-network --> +<!-- Generated from commit: 172cd5ab9919eda995b8162c87b84bea7d58fb3a --> diff --git a/keyboard-debug.docs.md b/keyboard-debug.docs.md index bc07e695..bd7ad5b3 100644 --- a/keyboard-debug.docs.md +++ b/keyboard-debug.docs.md @@ -1,3 +1,4 @@ Monitor keyboard input in real-time with this interactive keyboard debugger that displays pressed keys and their corresponding key codes. Press any keys on your keyboard to see them appear with visual feedback, including support for simultaneous multi-key presses and special key representations. This tool is useful for testing keyboard functionality, debugging input handling, and understanding key event properties like key name, code, and keyCode values. -<!-- Generated from commit: 696c234c2dd33f99e11e6172d4b7460ddc145401 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- Generated from commit: 696c234c2dd33f99e11e6172d4b7460ddc145401 --> diff --git a/keyboard-filters.docs.md b/keyboard-filters.docs.md index 2ffbd5ee..23fdecb5 100644 --- a/keyboard-filters.docs.md +++ b/keyboard-filters.docs.md @@ -2,4 +2,5 @@ Display and manage multiple filter conditions using an interactive badge interface with keyboard navigation support. Each filter badge displays a column name, operator, and value that can be edited individually, with options to add or remove filters as needed. The component provides full accessibility through keyboard shortcuts, focus management, and ARIA labels for screen reader users. -<!-- Generated from commit: 57dfbefb904856ce2ddeb5739093202b24790839 --> \ No newline at end of file +<!-- topics: css-layout, accessibility --> +<!-- Generated from commit: 57dfbefb904856ce2ddeb5739093202b24790839 --> diff --git a/lightning-timer.docs.md b/lightning-timer.docs.md index 17319a60..08cd542b 100644 --- a/lightning-timer.docs.md +++ b/lightning-timer.docs.md @@ -1,3 +1,5 @@ Track time with Lightning Timer, a full-screen countdown application that displays elapsed seconds in large, easy-to-read format. Click the timer display to start, pause, or reset the countdown, and access the settings icon to configure the total duration and optional warning threshold that triggers a visual color change. The timer supports URL-based configuration for quick setup and displays the remaining time in both the page and browser title bar. -<!-- Generated from commit: 7b5e57d73ca0a21fcb7f80cb6ce4bd1301fe06d8 --> \ No newline at end of file +<!-- topics: productivity --> +<!-- features: url-state --> +<!-- Generated from commit: 7b5e57d73ca0a21fcb7f80cb6ce4bd1301fe06d8 --> diff --git a/link-extractor.docs.md b/link-extractor.docs.md index 0a34fef1..ad56a370 100644 --- a/link-extractor.docs.md +++ b/link-extractor.docs.md @@ -1,3 +1,5 @@ Extract hyperlinks from pasted web content and export them in multiple formats including HTML, Markdown, and plain text. The tool automatically detects and removes duplicate links while displaying each link's title and URL for easy verification. Copy extracted links in your preferred format with a single click. -<!-- Generated from commit: daa72d910518f56743f4c97a6bfce23001d6c3c1 --> \ No newline at end of file +<!-- topics: developer-tools, productivity --> +<!-- features: clipboard --> +<!-- Generated from commit: daa72d910518f56743f4c97a6bfce23001d6c3c1 --> diff --git a/link-temp.docs.md b/link-temp.docs.md index ceb982fd..60d58a99 100644 --- a/link-temp.docs.md +++ b/link-temp.docs.md @@ -1,3 +1,4 @@ View Mozilla Bugzilla bug reports directly from your terminal using this LLM plugin for Google's Gemini API. The plugin enables seamless integration between your command-line workflow and Bugzilla's bug tracking system, allowing you to query and retrieve bug information without leaving your terminal environment. This tool is particularly useful for developers who want to incorporate bug data into their LLM-powered workflows and automation scripts. -<!-- Generated from commit: 457c6dec714c6f5da1713945c99e43ceb612f9e8 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- Generated from commit: 457c6dec714c6f5da1713945c99e43ceb612f9e8 --> diff --git a/llm-lib.docs.md b/llm-lib.docs.md index 414fa90e..a3e29c8e 100644 --- a/llm-lib.docs.md +++ b/llm-lib.docs.md @@ -1,3 +1,5 @@ This is an interactive demonstration of a unified JavaScript library that provides a consistent interface for working with multiple large language model providers. The tool allows users to seamlessly switch between OpenAI, Anthropic Claude, and Google Gemini while managing API keys and configuring system prompts. Both streaming and non-streaming response modes are supported, with real-time status updates and syntax-highlighted code examples showing how to integrate the library into projects. -<!-- Generated from commit: 5b63ef8fd4300ee0f35ceb3e4572748da3363e01 --> \ No newline at end of file +<!-- topics: ai-llm --> +<!-- features: local-storage, fetch-network --> +<!-- Generated from commit: 5b63ef8fd4300ee0f35ceb3e4572748da3363e01 --> diff --git a/lobsters-bookmarklet.docs.md b/lobsters-bookmarklet.docs.md index f627bdb2..56ef7cd9 100644 --- a/lobsters-bookmarklet.docs.md +++ b/lobsters-bookmarklet.docs.md @@ -1,3 +1,5 @@ Browse Lobste.rs comment threads with an enhanced "Latest" tab that displays all comments in chronological order with newest first, making it easier to catch up on recent discussion activity. The bookmarklet adds reply-to links showing parent comment relationships and includes a "Copy Thread" feature to export the entire discussion as numbered plain text. Installation is straightforward across desktop browsers and mobile Safari by dragging the bookmarklet to your bookmarks bar or copying the code manually on mobile devices. -<!-- Generated from commit: 8c4c61be7944ae66ac149e8c32d7f26458e5b39c --> \ No newline at end of file +<!-- topics: social-feeds --> +<!-- features: clipboard --> +<!-- Generated from commit: 8c4c61be7944ae66ac149e8c32d7f26458e5b39c --> diff --git a/manyana.docs.md b/manyana.docs.md index c7e20922..339df950 100644 --- a/manyana.docs.md +++ b/manyana.docs.md @@ -2,4 +2,6 @@ Explore how generation-counting conflict resolution works in distributed systems by editing two independent document branches and observing their deterministic merge. This interactive tool demonstrates the Manyana merge algorithm, where each state entry carries a count field that determines whether content is live (odd count) or deleted (even count)—allowing re-adds to automatically win over deletions during merge. Built with Python via Pyodide, it runs entirely in your browser with live rendering of merge trees, conflict detection, and detailed state inspection. -<!-- Generated from commit: 91ddc6c343064cca1482985e59603791ed1882cf --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- features: webassembly --> +<!-- Generated from commit: 91ddc6c343064cca1482985e59603791ed1882cf --> diff --git a/markdown-copy-component.docs.md b/markdown-copy-component.docs.md index 4b5bc77d..e67350a8 100644 --- a/markdown-copy-component.docs.md +++ b/markdown-copy-component.docs.md @@ -1,3 +1,5 @@ The `<markdown-copy>` component renders markdown content with built-in controls for viewing the rendered output and copying or viewing the source code. It provides an interactive interface with a menu button that allows users to toggle between the formatted markdown display and the raw markdown source, as well as quickly copy the markdown text to the clipboard. The component automatically handles indentation normalization and applies clean, readable styling to common markdown elements like headings, code blocks, blockquotes, and tables. -<!-- Generated from commit: aacc8801d6e6a1939e312bb0c6533c851cd4044e --> \ No newline at end of file +<!-- topics: text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: aacc8801d6e6a1939e312bb0c6533c851cd4044e --> diff --git a/markdown-math.docs.md b/markdown-math.docs.md index b8338a96..0b0d9633 100644 --- a/markdown-math.docs.md +++ b/markdown-math.docs.md @@ -1,3 +1,5 @@ Render Markdown text with integrated LaTeX mathematical equations in real-time as you type. This tool converts your input into formatted HTML output while simultaneously displaying a live preview with properly rendered math expressions using KaTeX. You can view the generated HTML code and copy it to your clipboard for use in other projects. -<!-- Generated from commit: b04b09214e110d93423059573d0198c46f981c65 --> \ No newline at end of file +<!-- topics: text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: b04b09214e110d93423059573d0198c46f981c65 --> diff --git a/markdown-svg-renderer.docs.md b/markdown-svg-renderer.docs.md index 35e13068..4a906f0f 100644 --- a/markdown-svg-renderer.docs.md +++ b/markdown-svg-renderer.docs.md @@ -1,3 +1,5 @@ View Mozilla Bugzilla bug reports and render formatted markdown content with live preview. Paste markdown directly or load from a raw URL or GitHub Gist, with support for standard markdown formatting, tables, code blocks, and interactive SVG previews with tabbed display. Toggle between editor and full-screen viewer modes to focus on the rendered output. -<!-- Generated from commit: befd53c835a08b273c4ee3582f0bad69e76494e2 --> \ No newline at end of file +<!-- topics: text-writing --> +<!-- features: svg, url-state, fetch-network --> +<!-- Generated from commit: befd53c835a08b273c4ee3582f0bad69e76494e2 --> diff --git a/mask-visualizer.docs.md b/mask-visualizer.docs.md index 36cc8c60..90056d5f 100644 --- a/mask-visualizer.docs.md +++ b/mask-visualizer.docs.md @@ -1,3 +1,4 @@ Visualize bounding boxes and PNG masks from JSON data with support for multiple coordinate system origins. This tool accepts JSON input containing box coordinates and base64-encoded mask images, then displays them overlaid on an interactive canvas with real-time coordinate transformation. The visualization includes detailed information about each item's original and transformed coordinates based on the selected origin point. -<!-- Generated from commit: e0cc858feb348a0430c056612c7c9aa5171e54ae --> \ No newline at end of file +<!-- topics: images-graphics, developer-tools --> +<!-- Generated from commit: e0cc858feb348a0430c056612c7c9aa5171e54ae --> diff --git a/mdn-timelines.docs.md b/mdn-timelines.docs.md index 7153d872..95752c63 100644 --- a/mdn-timelines.docs.md +++ b/mdn-timelines.docs.md @@ -1,3 +1,5 @@ View Mozilla's browser compatibility data to track when web APIs were first supported across different browsers. Search for any API by name to see a chronological timeline of support additions, including release dates and version numbers for each browser. The interface also displays relevant MDN documentation links, specification URLs, and status indicators to help developers understand the maturity and adoption timeline of web platform features. -<!-- Generated from commit: 41ce0b8bbae876c4abd9549ce34f13bb37f07c16 --> \ No newline at end of file +<!-- topics: reference-education, developer-tools --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: 41ce0b8bbae876c4abd9549ce34f13bb37f07c16 --> diff --git a/micropython.docs.md b/micropython.docs.md index c87ddd2e..bc054d5b 100644 --- a/micropython.docs.md +++ b/micropython.docs.md @@ -1,3 +1,5 @@ Execute Python code in a sandboxed MicroPython WebAssembly environment with output displayed in real-time. Code is automatically saved to the URL for convenient sharing and persistence, and the environment supports JavaScript interoperability including the `fetch()` API for making HTTP requests. Built-in examples demonstrate common programming patterns from basic operations to working with APIs. -<!-- Generated from commit: 425e8773f146b1678787bd972744fc309317849c --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: webassembly, url-state, fetch-network --> +<!-- Generated from commit: 425e8773f146b1678787bd972744fc309317849c --> diff --git a/microquickjs.docs.md b/microquickjs.docs.md index f6a9ed0e..d94deec3 100644 --- a/microquickjs.docs.md +++ b/microquickjs.docs.md @@ -1,3 +1,5 @@ Execute JavaScript code in a lightweight MicroQuickJS sandbox environment running via WebAssembly, with results displayed directly on the page. The sandbox supports ES5-like JavaScript features and automatically saves your code in the URL for easy sharing and recovery. Choose between optimized and original WebAssembly versions, try built-in examples, and use Ctrl+Enter to quickly run your code. -<!-- Generated from commit: a226383c7fc2643d4087fdfe9e52c780849bb270 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: webassembly, url-state --> +<!-- Generated from commit: a226383c7fc2643d4087fdfe9e52c780849bb270 --> diff --git a/milliseconds.docs.md b/milliseconds.docs.md index c7971c41..5fc3e6ef 100644 --- a/milliseconds.docs.md +++ b/milliseconds.docs.md @@ -1,3 +1,5 @@ Convert milliseconds into multiple time units with this interactive tool that displays the duration in seconds, minutes, hours, days, weeks, and a human-readable format. The converter accepts numbers with commas or underscores for readability and provides both a compact breakdown (e.g., "3 minutes, 7 seconds, 238 milliseconds") and a clock-format representation. Results can be copied to the clipboard with a single click for easy sharing or documentation. -<!-- Generated from commit: 207a3aeb4c060ebce99045068cadb83b00028f97 --> \ No newline at end of file +<!-- topics: productivity --> +<!-- features: clipboard --> +<!-- Generated from commit: 207a3aeb4c060ebce99045068cadb83b00028f97 --> diff --git a/minesweeper.docs.md b/minesweeper.docs.md index 8a609c50..51ac4c5e 100644 --- a/minesweeper.docs.md +++ b/minesweeper.docs.md @@ -1,3 +1,4 @@ Play a classic Minesweeper game directly in your browser with support for three difficulty levels: Easy, Medium, and Hard. Use left-click to reveal cells and right-click to place flags, or toggle between reveal and flag modes on mobile with long-press support. The game features a timer to track your speed, mine counter to monitor remaining flags, and immediate visual feedback when you win or hit a mine. -<!-- Generated from commit: 6ffa42047065a092de154650dc20ece10bbe9f41 --> \ No newline at end of file +<!-- topics: games-fun --> +<!-- Generated from commit: 6ffa42047065a092de154650dc20ece10bbe9f41 --> diff --git a/mobile-tables.docs.md b/mobile-tables.docs.md index 4227f518..2fc29cef 100644 --- a/mobile-tables.docs.md +++ b/mobile-tables.docs.md @@ -2,4 +2,6 @@ Explore interactive demonstrations of responsive table design patterns for mobile and narrow screens. This comprehensive guide covers twelve techniques—from horizontal scrolling and pinned columns to stacked cards, column toggling, accordion rows, container queries, comparison modes, and grid-based layouts—each with working code, accessibility features, and real-world use cases. Resize your browser or view on mobile to see how each pattern adapts to different viewport widths, and discover when to use each approach based on your data structure and user needs. -<!-- Generated from commit: b42bc5b51748a99f607729b659e04d7a3e1e745a --> \ No newline at end of file +<!-- topics: reference-education, css-layout --> +<!-- features: svg --> +<!-- Generated from commit: b42bc5b51748a99f607729b659e04d7a3e1e745a --> diff --git a/mp3-inspector.docs.md b/mp3-inspector.docs.md index 515a31ec..16737716 100644 --- a/mp3-inspector.docs.md +++ b/mp3-inspector.docs.md @@ -1,3 +1,5 @@ Extract ID3 metadata and file information from MP3 audio files using this browser-based tool. Upload an MP3 file by dragging it onto the drop zone or selecting it through the file picker, and the inspector will parse and display all available tags including title, artist, album art, technical encoding details, and embedded URLs. The tool organizes metadata into categorized sections and provides a raw JSON view for advanced inspection of the complete tag data. -<!-- Generated from commit: f0459f33e119d4e5aa757fb58b00798d8290a4c6 --> \ No newline at end of file +<!-- topics: audio-video, developer-tools --> +<!-- features: file-upload, drag-and-drop --> +<!-- Generated from commit: f0459f33e119d4e5aa757fb58b00798d8290a4c6 --> diff --git a/nav-for-headings.docs.md b/nav-for-headings.docs.md index acb46b96..f715f2fe 100644 --- a/nav-for-headings.docs.md +++ b/nav-for-headings.docs.md @@ -1,3 +1,4 @@ Process HTML content to automatically generate unique IDs for all header elements and create a table of contents with anchor links. This tool is useful for adding navigation functionality to static HTML pages or preparing content for documentation systems that require header identification. Simply paste your HTML and provide the page URL, then the processor will output the modified HTML and a formatted list of clickable header links. -<!-- Generated from commit: 2dbdc12b1eecf73a8a8b51c3b221774e149a2048 --> \ No newline at end of file +<!-- topics: developer-tools, text-writing --> +<!-- Generated from commit: 2dbdc12b1eecf73a8a8b51c3b221774e149a2048 --> diff --git a/new-yorker-style.docs.md b/new-yorker-style.docs.md index a18a9c8e..971f55ca 100644 --- a/new-yorker-style.docs.md +++ b/new-yorker-style.docs.md @@ -1,3 +1,5 @@ Convert text to match The New Yorker's distinctive typographic style, featuring proper diaereses (such as "coöperate" and "naïve"), curly quotation marks, em dashes, and ellipses. Paste your text into the input field and watch the refined version appear instantly in the output area, which can be copied to your clipboard with a single click. -<!-- Generated from commit: 27c0255038c88a8607b4bcd9f5ef0e66c614de4e --> \ No newline at end of file +<!-- topics: text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: 27c0255038c88a8607b4bcd9f5ef0e66c614de4e --> diff --git a/nicar-2026.docs.md b/nicar-2026.docs.md index c075fcce..3dda6790 100644 --- a/nicar-2026.docs.md +++ b/nicar-2026.docs.md @@ -1,3 +1,5 @@ Browse the NICAR 2026 conference schedule with powerful search and filtering capabilities. This interactive schedule viewer lets you explore sessions across multiple days, filter by session type, track, and skill level, and save your favorite sessions for quick access. The schedule works offline using cached data and automatically syncs updates when you're back online. -<!-- Generated from commit: c0f15cfa64cb5b6f30606d1dd78a4f774acf4c19 --> \ No newline at end of file +<!-- topics: productivity, social-feeds --> +<!-- features: local-storage, fetch-network, service-worker --> +<!-- Generated from commit: c0f15cfa64cb5b6f30606d1dd78a4f774acf4c19 --> diff --git a/notes-to-markdown.docs.md b/notes-to-markdown.docs.md index fc50cb2a..0a51d3b2 100644 --- a/notes-to-markdown.docs.md +++ b/notes-to-markdown.docs.md @@ -1,3 +1,5 @@ Convert Apple Notes content to Markdown and HTML formats while preserving hyperlinks and formatting. Paste your notes into the text area to automatically generate both Markdown and HTML outputs, with a live preview of the rendered content. The tool parses RTF data from Apple Notes and provides copy buttons for easy transfer of the converted content. -<!-- Generated from commit: 8dff45c03b3353aced9c4f7832d0609d8ca076aa --> \ No newline at end of file +<!-- topics: text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: 8dff45c03b3353aced9c4f7832d0609d8ca076aa --> diff --git a/numpy-pyodide-lab.docs.md b/numpy-pyodide-lab.docs.md index b0ba5811..c3e09f33 100644 --- a/numpy-pyodide-lab.docs.md +++ b/numpy-pyodide-lab.docs.md @@ -1,3 +1,5 @@ Execute NumPy vector and matrix operations directly in your browser using an interactive lab powered by Pyodide. Work through five hands-on exercises covering elementwise operations, dot products, matrix multiplication, broadcasting, and indexing, then experiment freely in the playground sandbox with instant Python output. -<!-- Generated from commit: e862c3e3f7bc21edfb7841e6fd02c7c9a2963eca --> \ No newline at end of file +<!-- topics: reference-education, developer-tools --> +<!-- features: webassembly --> +<!-- Generated from commit: e862c3e3f7bc21edfb7841e6fd02c7c9a2963eca --> diff --git a/ocr.docs.md b/ocr.docs.md index ac4f5d5e..b0896714 100644 --- a/ocr.docs.md +++ b/ocr.docs.md @@ -1,3 +1,5 @@ Extract text from PDF documents and images using optical character recognition (OCR) directly in your browser. The tool leverages Tesseract.js for text recognition and PDF.js to handle multi-page PDF files, supporting multiple languages and file formats including JPEG, PNG, and GIF. All processing occurs locally in your browser with no files being transmitted to external servers. -<!-- Generated from commit: c335adf1faeb762d474771d17a2d0c8e41204fb0 --> \ No newline at end of file +<!-- topics: documents-pdf, images-graphics --> +<!-- features: file-upload, drag-and-drop, canvas, url-state --> +<!-- Generated from commit: c335adf1faeb762d474771d17a2d0c8e41204fb0 --> diff --git a/octave-explainer.docs.md b/octave-explainer.docs.md index a4c96ea1..29226570 100644 --- a/octave-explainer.docs.md +++ b/octave-explainer.docs.md @@ -1,3 +1,5 @@ Explore the mathematical and sonic relationship between frequencies through interactive demonstrations and a playable piano keyboard. This educational tool visualizes how an octave represents a 2:1 frequency ratio, allowing you to hear the harmonic connection between notes that sound identical yet exist at different pitches. Experiment with various base frequencies using the slider to understand how this fundamental musical principle scales across the entire spectrum. -<!-- Generated from commit: 10ea8c02f4b3f53324c7599ff3a56aa15f1e1806 --> \ No newline at end of file +<!-- topics: reference-education, audio-video --> +<!-- features: web-audio, canvas --> +<!-- Generated from commit: 10ea8c02f4b3f53324c7599ff3a56aa15f1e1806 --> diff --git a/omit-needless-words.docs.md b/omit-needless-words.docs.md index 7e6ed029..319723f2 100644 --- a/omit-needless-words.docs.md +++ b/omit-needless-words.docs.md @@ -2,4 +2,6 @@ Analyze text to identify unnecessary words and phrases using Claude's writing expertise. This tool applies the principle of omitting needless words from Strunk & White's writing guide, marking removable words while preserving grammatical correctness and meaning. Simply paste your text, select a Claude model, and the application will highlight words that can be safely cut from your writing. -<!-- Generated from commit: 5b63ef8fd4300ee0f35ceb3e4572748da3363e01 --> \ No newline at end of file +<!-- topics: text-writing, ai-llm --> +<!-- features: local-storage, fetch-network --> +<!-- Generated from commit: 5b63ef8fd4300ee0f35ceb3e4572748da3363e01 --> diff --git a/open-sauce-2025.docs.md b/open-sauce-2025.docs.md index 95d55c36..5b86976c 100644 --- a/open-sauce-2025.docs.md +++ b/open-sauce-2025.docs.md @@ -1,3 +1,5 @@ Browse the Open Sauce 2025 conference schedule with sessions organized by day, including speaker information, session duration, location, and detailed descriptions. Users can search for specific sessions across all three conference days (July 18-20, 2025) and download the entire schedule as an ICS calendar file for integration with their calendar applications. The interface displays current and upcoming sessions in Pacific Time to help attendees plan their conference experience. -<!-- Generated from commit: 7e6a4c6f58a2babe500db9222bce8bc0b7cda80c --> \ No newline at end of file +<!-- topics: productivity --> +<!-- features: fetch-network --> +<!-- Generated from commit: 7e6a4c6f58a2babe500db9222bce8bc0b7cda80c --> diff --git a/openai-audio-output.docs.md b/openai-audio-output.docs.md index a9feadb8..bf2f5d1e 100644 --- a/openai-audio-output.docs.md +++ b/openai-audio-output.docs.md @@ -1,3 +1,5 @@ Interact with OpenAI's GPT-4o audio models to generate spoken responses to your prompts with customizable system instructions and voice selection. The application processes your input through the OpenAI API, retrieves the generated audio and transcript, and provides playback controls along with the full API response data. You can save responses as GitHub Gists and download the audio files for offline use. -<!-- Generated from commit: fdfb6f124df0b26465df11414558634f3c0900ad --> \ No newline at end of file +<!-- topics: ai-llm, audio-video --> +<!-- features: fetch-network, local-storage, clipboard --> +<!-- Generated from commit: fdfb6f124df0b26465df11414558634f3c0900ad --> diff --git a/openai-audio.docs.md b/openai-audio.docs.md index 5b6504f8..25897659 100644 --- a/openai-audio.docs.md +++ b/openai-audio.docs.md @@ -1,3 +1,5 @@ Record audio through your microphone and send it to OpenAI's GPT-4o audio model along with a text prompt to receive AI-generated responses. The tool converts your recorded audio to WAV format, calculates token usage and associated costs for both text and audio inputs, and displays the API response in both formatted and raw JSON views. Your API key is securely stored locally in your browser, and you can download the recorded audio file for later use. -<!-- Generated from commit: 1c63c27fa658f88da2c2928449f28ddb1c3c16c0 --> \ No newline at end of file +<!-- topics: ai-llm, audio-video --> +<!-- features: camera-mic, web-audio, file-upload, fetch-network, local-storage --> +<!-- Generated from commit: 1c63c27fa658f88da2c2928449f28ddb1c3c16c0 --> diff --git a/openai-webrtc.docs.md b/openai-webrtc.docs.md index c2cf0f27..765b1d39 100644 --- a/openai-webrtc.docs.md +++ b/openai-webrtc.docs.md @@ -1,3 +1,5 @@ Establish real-time audio conversations with OpenAI's GPT realtime models using WebRTC technology. This interface allows you to select from multiple voice options and different model versions, monitoring detailed token usage and costs for each interaction and across your entire session. All API tokens are stored locally in your browser for convenience. -<!-- Generated from commit: a9bccc13fd904bd2b51177bea085f86b6eb5cad8 --> \ No newline at end of file +<!-- topics: ai-llm, audio-video --> +<!-- features: webrtc, camera-mic, web-audio, local-storage, fetch-network --> +<!-- Generated from commit: a9bccc13fd904bd2b51177bea085f86b6eb5cad8 --> diff --git a/openfreemap-demo.docs.md b/openfreemap-demo.docs.md index 79d515b2..30415040 100644 --- a/openfreemap-demo.docs.md +++ b/openfreemap-demo.docs.md @@ -1,3 +1,4 @@ Explore an interactive map of San Francisco rendered with MapLibre GL and OpenFreeMap tiles, displaying 1000 randomly distributed markers across the city. The demo showcases three different approaches for rendering large numbers of points—scaled markers, custom HTML elements, and GeoJSON circle layers—with the map automatically adjusted to fit all markers in view. Users can interact with the tilted 3D map to navigate and explore the marker distribution across the San Francisco area. -<!-- Generated from commit: 450728011c3a103bcd44b2f4440d3dcc56a651a6 --> \ No newline at end of file +<!-- topics: maps-geo --> +<!-- Generated from commit: 450728011c3a103bcd44b2f4440d3dcc56a651a6 --> diff --git a/passkeys.docs.md b/passkeys.docs.md index fe57efb4..eb8b64c0 100644 --- a/passkeys.docs.md +++ b/passkeys.docs.md @@ -1,3 +1,5 @@ Experiment with passkey registration and authentication using the WebAuthn API in your browser. This demo allows you to create passkey credentials, authenticate with them, and inspect the underlying protocol responses and data. Stored credentials are maintained locally in your browser's storage, making this a fully client-side implementation for learning how modern passwordless authentication works. -<!-- Generated from commit: 6b0d8cdc263599b8460c5d2c77b78ab57f15d11e --> \ No newline at end of file +<!-- topics: developer-tools, encoding-security --> +<!-- features: local-storage --> +<!-- Generated from commit: 6b0d8cdc263599b8460c5d2c77b78ab57f15d11e --> diff --git a/paste-html-subset.docs.md b/paste-html-subset.docs.md index f5e723f4..73d1164e 100644 --- a/paste-html-subset.docs.md +++ b/paste-html-subset.docs.md @@ -1,3 +1,5 @@ Convert rich text content from clipboard into clean, filtered HTML containing only semantic elements like paragraphs, headings, lists, links, and text formatting. Paste formatted content into the editable area to automatically extract and sanitize the HTML, removing unsupported tags and attributes while preserving the document structure and links. The cleaned HTML is displayed in a code editor and rendered in a live preview, with options to copy the code or clear all content. -<!-- Generated from commit: 6f910f4c39655775c56d02ce6e4a4693d2cfdc42 --> \ No newline at end of file +<!-- topics: developer-tools, text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: 6f910f4c39655775c56d02ce6e4a4693d2cfdc42 --> diff --git a/paste-rich-text.docs.md b/paste-rich-text.docs.md index 0c33ac8d..bd3694d2 100644 --- a/paste-rich-text.docs.md +++ b/paste-rich-text.docs.md @@ -1,3 +1,5 @@ Extract HTML code from formatted text by pasting rich content into this tool, which automatically captures and displays the underlying HTML markup. The tool provides both the raw HTML code for editing and a live preview of how the formatted content renders. Use the copy button to quickly transfer the extracted HTML to your clipboard, or clear the interface to process new content. -<!-- Generated from commit: 49c382ea7f933d489d57cc434db2314f1120886b --> \ No newline at end of file +<!-- topics: developer-tools, text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: 49c382ea7f933d489d57cc434db2314f1120886b --> diff --git a/pasted-file-editor.docs.md b/pasted-file-editor.docs.md index 59e89970..e5143660 100644 --- a/pasted-file-editor.docs.md +++ b/pasted-file-editor.docs.md @@ -1,3 +1,5 @@ View and manage text drafts with automatic file attachment capabilities. Paste files or text content of 1,000 characters or more to attach them below the editor while keeping your draft text unchanged. Preview attached files in a modal or remove them using drag-and-drop, file selection, or clipboard paste. -<!-- Generated from commit: 39e448940ba065ff161aed9203f94f65859541d9 --> \ No newline at end of file +<!-- topics: productivity, text-writing --> +<!-- features: clipboard, drag-and-drop, file-upload --> +<!-- Generated from commit: 39e448940ba065ff161aed9203f94f65859541d9 --> diff --git a/percentage-recalculator.docs.md b/percentage-recalculator.docs.md index 2a2f3184..a3cef837 100644 --- a/percentage-recalculator.docs.md +++ b/percentage-recalculator.docs.md @@ -1,3 +1,4 @@ Calculate and normalize multiple percentages to sum to 100%, with the option to exclude specific values from the recalculation. Enter up to four percentage values and check the "Ignore this" box next to any percentages you want to exclude; the tool will automatically recalculate the remaining percentages proportionally so they add up to 100%. -<!-- Generated from commit: 417e7ad6970acf77842caa52d1eb00c4761f1c5f --> \ No newline at end of file +<!-- topics: productivity --> +<!-- Generated from commit: 417e7ad6970acf77842caa52d1eb00c4761f1c5f --> diff --git a/pge-outages-hmb.docs.md b/pge-outages-hmb.docs.md index 08706b06..09c21645 100644 --- a/pge-outages-hmb.docs.md +++ b/pge-outages-hmb.docs.md @@ -1,3 +1,5 @@ Track power outages affecting the Half Moon Bay area with this interactive map displaying real-time PG&E outage data within a 15-mile radius. The application visualizes outage locations as point markers and affected areas as polygons, while displaying key statistics including the number of outages, impacted customers, and affected regions. Custom markers can be added by providing a URL parameter, and the map automatically refreshes every five minutes to ensure current outage information. -<!-- Generated from commit: e16c9e2b9a22af490321366dc98282a4915107d6 --> \ No newline at end of file +<!-- topics: maps-geo --> +<!-- features: fetch-network, local-storage, url-state --> +<!-- Generated from commit: e16c9e2b9a22af490321366dc98282a4915107d6 --> diff --git a/php-deserializer.docs.md b/php-deserializer.docs.md index a93d01a5..f2718054 100644 --- a/php-deserializer.docs.md +++ b/php-deserializer.docs.md @@ -1,3 +1,5 @@ Convert serialized PHP data to JSON format for easy viewing and manipulation. Paste your PHP serialized string into the input field to automatically parse and display the equivalent JSON output. Use the copy button to quickly transfer the JSON to your clipboard. -<!-- Generated from commit: 4c11c72c3badd4f2754287461b3c3b1a5dfc8d73 --> \ No newline at end of file +<!-- topics: developer-tools, data-json --> +<!-- features: clipboard --> +<!-- Generated from commit: 4c11c72c3badd4f2754287461b3c3b1a5dfc8d73 --> diff --git a/pipfile.docs.md b/pipfile.docs.md index e4d3b66f..11771711 100644 --- a/pipfile.docs.md +++ b/pipfile.docs.md @@ -1,3 +1,5 @@ Parse Pipfile.lock files to extract Python package dependencies and convert them into multiple formats for easy management and sharing. The tool automatically extracts package names and versions from the lock file and displays them in both Pipfile and requirements.txt formats, with one-click copying functionality for each output format. -<!-- Generated from commit: 0a11eb24ddca33a9315f879b170e8dad3399c719 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: clipboard --> +<!-- Generated from commit: 0a11eb24ddca33a9315f879b170e8dad3399c719 --> diff --git a/pomodoro.docs.md b/pomodoro.docs.md index 61549370..aa24978d 100644 --- a/pomodoro.docs.md +++ b/pomodoro.docs.md @@ -1,3 +1,5 @@ Track productivity sessions with this Pomodoro timer application that manages timed work intervals with customizable durations. Set a goal for each session, choose from preset time intervals ranging from 5 to 60 minutes, and pause or resume as needed while the timer counts down. All session data including start times, end times, and pause history is automatically saved and displayed in a detailed log table, with the ability to export the data as JSON for further analysis or record-keeping. -<!-- Generated from commit: ddaf7da00e9e76d7a0d986d5cb3b5d8fe0ea7e7c --> \ No newline at end of file +<!-- topics: productivity --> +<!-- features: local-storage --> +<!-- Generated from commit: ddaf7da00e9e76d7a0d986d5cb3b5d8fe0ea7e7c --> diff --git a/pretext-explainer.docs.md b/pretext-explainer.docs.md index 1a502311..50dc9a0f 100644 --- a/pretext-explainer.docs.md +++ b/pretext-explainer.docs.md @@ -1,3 +1,5 @@ Explore how pure-JavaScript text measurement and line breaking work through an interactive visualization of the Pretext library's pipeline. This tool demonstrates each stage from raw text input through whitespace normalization, word segmentation, canvas-based width measurement, and arithmetic-based line breaking, with live verification against actual DOM rendering. Drag sliders, switch fonts, and test different text samples to see how the engine handles emojis, CJK characters, Arabic text, and complex punctuation rules — all computed without touching the DOM. -<!-- Generated from commit: d8deb83eccc52c604277da785fe489f421d6f3d5 --> \ No newline at end of file +<!-- topics: reference-education, developer-tools --> +<!-- features: canvas --> +<!-- Generated from commit: d8deb83eccc52c604277da785fe489f421d6f3d5 --> diff --git a/progress.docs.md b/progress.docs.md index e21e6ec7..3427f5a7 100644 --- a/progress.docs.md +++ b/progress.docs.md @@ -1,3 +1,4 @@ Track the progress of the current U.S. presidential term with real-time statistics and a visual progress bar. The page displays elapsed and remaining days, percentage completion, and specific metrics related to the midterm election cycle scheduled for November 3, 2026. Information updates automatically to provide current data on the four-year term that began on January 20, 2025. -<!-- Generated from commit: 7adcf4db27092b017d18ea516f727d80846f197f --> \ No newline at end of file +<!-- topics: productivity --> +<!-- Generated from commit: 7adcf4db27092b017d18ea516f727d80846f197f --> diff --git a/prompt-caching.docs.md b/prompt-caching.docs.md index a5d15da5..9586c21c 100644 --- a/prompt-caching.docs.md +++ b/prompt-caching.docs.md @@ -1,3 +1,5 @@ Explore OpenAI's prompt caching feature by testing different prompt structures and observing cache hit rates across multiple requests. This interactive playground lets you compose system instructions, document context, and user questions, then send them to the Chat Completions or Responses API to track how cached tokens reduce costs and improve performance. Load pre-built scenarios to compare caching behavior—such as sending identical instructions with different questions to see cache hits, or swapping documents while keeping instructions static to measure prefix reuse. -<!-- Generated from commit: 1d6baf40110241775a4260d330a28cd23cb5cfd9 --> \ No newline at end of file +<!-- topics: ai-llm, developer-tools --> +<!-- features: fetch-network, local-storage --> +<!-- Generated from commit: 1d6baf40110241775a4260d330a28cd23cb5cfd9 --> diff --git a/prompts-js.docs.md b/prompts-js.docs.md index ff71e83f..8cb57e12 100644 --- a/prompts-js.docs.md +++ b/prompts-js.docs.md @@ -1,3 +1,4 @@ Prompts.js is a lightweight JavaScript library that provides modal dialog functionality for creating alert, confirm, and prompt interactions in web applications. The library enables developers to display user-facing dialogs with async/await syntax, making it easy to handle user responses in a clean, readable manner. This demo page allows you to test the three core dialog types and view the results of user interactions. -<!-- Generated from commit: 3d76b539136afa6310dfc1bdcb681f4d038f5253 --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- Generated from commit: 3d76b539136afa6310dfc1bdcb681f4d038f5253 --> diff --git a/pyodide-bar-chart.docs.md b/pyodide-bar-chart.docs.md index 7ea9f310..41681398 100644 --- a/pyodide-bar-chart.docs.md +++ b/pyodide-bar-chart.docs.md @@ -1,3 +1,5 @@ Execute Python code directly in your browser with Pyodide, a WebAssembly-based Python runtime. This demo loads pandas, numpy, and matplotlib in the client to generate a bar chart from sample data and display it as a rendered image—no server required. The first run may take a few seconds as the necessary libraries are downloaded from CDN, but subsequent executions run instantly from your browser's cache. -<!-- Generated from commit: d80768be9e8be887ed256c5098687463b08b070d --> \ No newline at end of file +<!-- topics: data-visualization --> +<!-- features: webassembly --> +<!-- Generated from commit: d80768be9e8be887ed256c5098687463b08b070d --> diff --git a/pyodide-repl.docs.md b/pyodide-repl.docs.md index 0bf57502..cad3757d 100644 --- a/pyodide-repl.docs.md +++ b/pyodide-repl.docs.md @@ -1,3 +1,5 @@ Execute Python code directly in your web browser using Pyodide, a port of CPython to WebAssembly. This REPL provides an interactive Python environment with support for multiple Pyodide versions, single-line and multi-line input modes, and command history navigation. The interface is optimized for both desktop and mobile devices, with a dark theme and responsive layout that prevents content from being hidden behind on-screen keyboards. -<!-- Generated from commit: 16e1d75e895b23d90e56019c13b3eb892c2cc1a9 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: webassembly, url-state --> +<!-- Generated from commit: 16e1d75e895b23d90e56019c13b3eb892c2cc1a9 --> diff --git a/pypi-changelog.docs.md b/pypi-changelog.docs.md index fe0e58f7..f1e0bc33 100644 --- a/pypi-changelog.docs.md +++ b/pypi-changelog.docs.md @@ -2,4 +2,6 @@ Track code changes across Python package versions by comparing wheel distributions from PyPI. Enter any package name to view all released versions with wheel files and generate side-by-side diffs of the changes between any two versions. The tool extracts and compares all text files from the wheels, intelligently handling binary files and package metadata renames while preserving the full context of modifications. -<!-- Generated from commit: 725b699d9cd14fffee0ca6bc529cf4565017ca0c --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, clipboard, url-state --> +<!-- Generated from commit: 725b699d9cd14fffee0ca6bc529cf4565017ca0c --> diff --git a/python-comment-stripper.docs.md b/python-comment-stripper.docs.md index fcb04842..ca668f98 100644 --- a/python-comment-stripper.docs.md +++ b/python-comment-stripper.docs.md @@ -1,3 +1,5 @@ Remove all comments from Python source code while preserving strings, docstrings, and code structure using the `tokenize` module running on Pyodide. Paste your Python code into the input panel, and the tool automatically strips comments in real-time, with the ability to copy the cleaned output to your clipboard. The application runs entirely in the browser without requiring a local Python installation. -<!-- Generated from commit: f763a6ea5887c08e0b8bc45e03b1466d14e78c02 --> \ No newline at end of file +<!-- topics: developer-tools, text-writing --> +<!-- features: webassembly, clipboard --> +<!-- Generated from commit: f763a6ea5887c08e0b8bc45e03b1466d14e78c02 --> diff --git a/python-vulnerability-lookup.docs.md b/python-vulnerability-lookup.docs.md index 96891415..6dde4cee 100644 --- a/python-vulnerability-lookup.docs.md +++ b/python-vulnerability-lookup.docs.md @@ -1,3 +1,5 @@ Search Python packages for known security vulnerabilities by pasting a `pyproject.toml` or `requirements.txt` file, or by loading dependencies directly from a GitHub repository. The tool queries the OSV.dev vulnerability database and displays detailed information about any identified vulnerabilities, including severity levels, affected version ranges, and links to full disclosure reports. -<!-- Generated from commit: d9bada923955fcb60708b9271a303b2722a44e5c --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, clipboard, url-state --> +<!-- Generated from commit: d9bada923955fcb60708b9271a303b2722a44e5c --> diff --git a/qr-code-generator.docs.md b/qr-code-generator.docs.md index 1e6785c1..3582091a 100644 --- a/qr-code-generator.docs.md +++ b/qr-code-generator.docs.md @@ -1,3 +1,5 @@ Generate scannable QR codes from URLs, text, or WiFi network details with customizable styling options. The tool supports multiple encoding modes, including WiFi networks with security settings, and offers various visual styles such as square or liquid designs with adjustable sizes and colors. Generated codes can be downloaded as PNG images or copied directly to the clipboard. -<!-- Generated from commit: 8116af397b485d39dfd3f41b1d07c518da67ad7a --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: canvas, clipboard --> +<!-- Generated from commit: 8116af397b485d39dfd3f41b1d07c518da67ad7a --> diff --git a/qr.docs.md b/qr.docs.md index da4693e0..74b19a08 100644 --- a/qr.docs.md +++ b/qr.docs.md @@ -1,3 +1,5 @@ Decode QR codes from images or your device's camera with this interactive web application. Upload an image by dragging and dropping, clicking to select a file, or pasting from your clipboard, and the decoder will extract the encoded data instantly. Switch to webcam mode for real-time scanning with support for multiple cameras and pinch-to-zoom functionality on touch devices. -<!-- Generated from commit: d4336f4693a0ab5a417d152d6ce79b9bf1325f10 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: canvas, drag-and-drop, file-upload, camera-mic --> +<!-- Generated from commit: d4336f4693a0ab5a417d152d6ce79b9bf1325f10 --> diff --git a/query-string-stripper.docs.md b/query-string-stripper.docs.md index 131d8961..a55fa950 100644 --- a/query-string-stripper.docs.md +++ b/query-string-stripper.docs.md @@ -1,3 +1,5 @@ Remove query parameters and tracking data from URLs with this Query String Stripper tool. Paste any URL to instantly extract the base address by stripping away everything after the question mark, then copy the cleaned result to your clipboard with a single click. This utility is helpful for sharing clean URLs, removing analytics parameters, or simplifying web addresses for documentation purposes. -<!-- Generated from commit: f7010753d1508f56a225c6cddf84e9cc78936ff4 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: clipboard --> +<!-- Generated from commit: f7010753d1508f56a225c6cddf84e9cc78936ff4 --> diff --git a/quickjs.docs.md b/quickjs.docs.md index e7d78b24..3d46c2ff 100644 --- a/quickjs.docs.md +++ b/quickjs.docs.md @@ -1,3 +1,5 @@ Execute JavaScript code in a sandboxed QuickJS WebAssembly environment with a built-in synchronous `fetch()` function for retrieving remote content. Code is automatically encoded in the URL hash, allowing you to easily share executable snippets with others. The interface provides a collection of ready-to-run examples covering common programming tasks and JavaScript features, making it useful for learning, testing, and demonstrating code behavior. -<!-- Generated from commit: a226383c7fc2643d4087fdfe9e52c780849bb270 --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- features: webassembly, url-state, clipboard, fetch-network --> +<!-- Generated from commit: a226383c7fc2643d4087fdfe9e52c780849bb270 --> diff --git a/reading-time.docs.md b/reading-time.docs.md index 05e4bc7b..5ea60804 100644 --- a/reading-time.docs.md +++ b/reading-time.docs.md @@ -1,3 +1,4 @@ Calculate reading time estimates for any text by pasting or typing content into the input area. The tool displays real-time statistics including word count, character count, and estimated reading duration based on an average reading speed of 230 words per minute. The reading time adjusts dynamically, showing minutes for shorter texts and hours plus minutes for longer content. -<!-- Generated from commit: 184097807535239e910ed4db40bad2190a9efd11 --> \ No newline at end of file +<!-- topics: productivity, text-writing --> +<!-- Generated from commit: 184097807535239e910ed4db40bad2190a9efd11 --> diff --git a/red-extractor.docs.md b/red-extractor.docs.md index 3c58b107..4b0e7fb4 100644 --- a/red-extractor.docs.md +++ b/red-extractor.docs.md @@ -2,4 +2,6 @@ Extract red annotations from AI-generated annotated images and overlay them onto your original photos. This tool isolates red markings (circles, arrows, highlights, text) from images created by AI services like ChatGPT, Gemini, or similar platforms, then optionally applies them to your unmodified original image. The red sensitivity slider allows you to control which shades of red are detected, making it easy to capture all annotation colors while maintaining transparency elsewhere in the image. -<!-- Generated from commit: f96f7e9b2f9b3c36541bef1ac3ba1e202f91837d --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, file-upload, drag-and-drop --> +<!-- Generated from commit: f96f7e9b2f9b3c36541bef1ac3ba1e202f91837d --> diff --git a/redis-array.docs.md b/redis-array.docs.md index 1982c6fc..e5820bb0 100644 --- a/redis-array.docs.md +++ b/redis-array.docs.md @@ -2,4 +2,6 @@ Explore Redis array commands in an interactive web-based environment compiled to WebAssembly. This playground lets you execute AR* commands against an in-memory Redis instance, visualize keyspace contents, and inspect command documentation with live syntax previews. The implementation uses the sparse array data structure from the antirez:array branch, exposing commands like ARSET, ARGET, ARGREP, and others alongside a console that displays all executed commands and their responses. -<!-- Generated from commit: 69d05ef2c5e267f0600e379bc758e22d8d544e58 --> \ No newline at end of file +<!-- topics: developer-tools, sqlite-databases --> +<!-- features: webassembly, local-storage --> +<!-- Generated from commit: 69d05ef2c5e267f0600e379bc758e22d8d544e58 --> diff --git a/render-claude-citations.docs.md b/render-claude-citations.docs.md index b4ef038e..d9a641f9 100644 --- a/render-claude-citations.docs.md +++ b/render-claude-citations.docs.md @@ -1,3 +1,4 @@ Render Claude API responses with proper citation formatting by pasting JSON output into this tool. The tool parses the response structure and displays text content alongside blockquote-formatted citations, making it easy to review how Claude has sourced and attributed information. An embedded iframe renderer safely displays the formatted output with styling that highlights cited passages. -<!-- Generated from commit: d97ff4e32f32e064c3fa0c26f1efba6d32655355 --> \ No newline at end of file +<!-- topics: ai-llm, developer-tools --> +<!-- Generated from commit: d97ff4e32f32e064c3fa0c26f1efba6d32655355 --> diff --git a/render-markdown.docs.md b/render-markdown.docs.md index 3ec4ba96..3cf541d5 100644 --- a/render-markdown.docs.md +++ b/render-markdown.docs.md @@ -1,3 +1,5 @@ Convert markdown text to HTML using GitHub's markdown rendering API. The tool provides a live preview of the rendered output and allows you to copy the generated HTML or rich text to your clipboard. Additional options include GitHub Flavored Markdown support and automatic cleanup of hidden HTML elements and metadata. -<!-- Generated from commit: 91bfd29ff0279ad7e7666b1f6047ab571007990c --> \ No newline at end of file +<!-- topics: text-writing, developer-tools --> +<!-- features: fetch-network, clipboard --> +<!-- Generated from commit: 91bfd29ff0279ad7e7666b1f6047ab571007990c --> diff --git a/rich-text-to-markdown.docs.md b/rich-text-to-markdown.docs.md index 1cc61988..e236546c 100644 --- a/rich-text-to-markdown.docs.md +++ b/rich-text-to-markdown.docs.md @@ -1,3 +1,5 @@ Convert rich text formats into properly formatted Markdown by pasting content into the text area. The tool automatically detects and converts formatting such as bold, italic, links, code blocks, headings, and lists while removing unnecessary leading spaces from each line. Supports rich text from multiple sources including RTF, HTML, and plain text formats. -<!-- Generated from commit: bf0b1ef22effa52bfdd620c1f82c7e1dd1aedd10 --> \ No newline at end of file +<!-- topics: text-writing --> +<!-- features: clipboard --> +<!-- Generated from commit: bf0b1ef22effa52bfdd620c1f82c7e1dd1aedd10 --> diff --git a/rtf-to-html.docs.md b/rtf-to-html.docs.md index 5897f679..e78237b2 100644 --- a/rtf-to-html.docs.md +++ b/rtf-to-html.docs.md @@ -1,3 +1,5 @@ Convert Rich Text Format (RTF) documents to HTML with preserved formatting, colors, and styling. Paste RTF content from your clipboard to automatically extract the color table and convert text formatting including bold styling, text colors, and background colors into inline HTML styles. The converter displays the raw RTF data, generated HTML code, and a live preview of the formatted output all in one interface. -<!-- Generated from commit: 20db4718bdf4d2f5bc8c354f345fdde34cfc650e --> \ No newline at end of file +<!-- topics: text-writing, developer-tools --> +<!-- features: clipboard --> +<!-- Generated from commit: 20db4718bdf4d2f5bc8c354f345fdde34cfc650e --> diff --git a/schema-dsl.docs.md b/schema-dsl.docs.md index dc624037..610aa0fc 100644 --- a/schema-dsl.docs.md +++ b/schema-dsl.docs.md @@ -1,3 +1,4 @@ Convert a compact schema definition language into JSON schema format in real-time. This tool accepts a concise DSL where you specify field names, types (str, int, float, bool), and optional descriptions, then automatically generates the corresponding JSON schema. The converter supports both object schemas and array item schemas through the "Array items schema" option. -<!-- Generated from commit: e3f47637ebdf7e83155643cae1c0def78c7caf93 --> \ No newline at end of file +<!-- topics: developer-tools, data-json --> +<!-- Generated from commit: e3f47637ebdf7e83155643cae1c0def78c7caf93 --> diff --git a/side-panel-dialog.docs.md b/side-panel-dialog.docs.md index 4584ecbd..c9d76c8e 100644 --- a/side-panel-dialog.docs.md +++ b/side-panel-dialog.docs.md @@ -1,3 +1,4 @@ Explore a product catalog with interactive item details displayed in a smooth side panel modal. Click any product card to view comprehensive information including category, price, and description, with the option to toggle between modal and non-modal dialog behavior. The interface includes a feedback form within the side panel, allowing users to submit comments about products with a seamless animated experience. -<!-- Generated from commit: be33e66f67892ada5d365182c4d2d7e5bf48fffc --> \ No newline at end of file +<!-- topics: reference-education, css-layout --> +<!-- Generated from commit: be33e66f67892ada5d365182c4d2d7e5bf48fffc --> diff --git a/sloccount.docs.md b/sloccount.docs.md index fffbceb4..0a2ba313 100644 --- a/sloccount.docs.md +++ b/sloccount.docs.md @@ -2,4 +2,6 @@ Count lines of code in source files across multiple programming languages using SLOCCount algorithms compiled to WebAssembly. This tool analyzes code from pasted snippets, GitHub repositories, or uploaded ZIP files, providing detailed breakdowns by language along with COCOMO-based effort and cost estimates. The analysis runs entirely in your browser using the actual SLOCCount Perl scripts and C-based counters compiled to WebAssembly for fast, privacy-preserving processing. -<!-- Generated from commit: 4d3809c45b6a702903d43733bcaf51b1cf340e7c --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: webassembly, file-upload, fetch-network --> +<!-- Generated from commit: 4d3809c45b6a702903d43733bcaf51b1cf340e7c --> diff --git a/social-media-cropper.docs.md b/social-media-cropper.docs.md index 2c1c3057..a7cf4aed 100644 --- a/social-media-cropper.docs.md +++ b/social-media-cropper.docs.md @@ -1,3 +1,5 @@ Crop and customize images for social media platforms with precise control over composition and framing. This tool supports multiple popular aspect ratios including Twitter/LinkedIn (2:1), Facebook (1.91:1), Substack (1.4:1), and Instagram (1:1), with an intelligent background color detection system that automatically matches the image's edge tones. The interface offers both mouse and touch-friendly controls, including press-and-hold zoom buttons, pinch-to-zoom on mobile devices, and toggleable drag modes to move either the image or the crop box. -<!-- Generated from commit: 152fd93b7a6fdd3447ec55798e54dbef1630b911 --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, file-upload, drag-and-drop --> +<!-- Generated from commit: 152fd93b7a6fdd3447ec55798e54dbef1630b911 --> diff --git a/software-heritage-repo.docs.md b/software-heritage-repo.docs.md index 53c8dbcd..31d4c53b 100644 --- a/software-heritage-repo.docs.md +++ b/software-heritage-repo.docs.md @@ -1,3 +1,5 @@ Download archived Git repositories from Software Heritage, the universal archive of software source code. This tool queries the Software Heritage GraphQL API to locate repositories and creates downloadable bare Git archives through the vault service. Enter a repository URL to retrieve the latest snapshot and access detailed archive information including the Software Heritage identifier (SWHID) for future reference. -<!-- Generated from commit: dc4748ca4471e30f9fd8b108c99d918fb5f65a43 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: dc4748ca4471e30f9fd8b108c99d918fb5f65a43 --> diff --git a/sort-algorithms.docs.md b/sort-algorithms.docs.md index dd09a891..10770d51 100644 --- a/sort-algorithms.docs.md +++ b/sort-algorithms.docs.md @@ -1,3 +1,4 @@ Explore and compare different sorting algorithms through interactive animated visualizations that display how each algorithm organizes data in real-time. The tool allows you to adjust dataset size and animation speed, run individual algorithms step-by-step or continuously, and race multiple algorithms simultaneously to see which performs best. Each algorithm includes detailed complexity analysis and visual indicators for comparisons, swaps, and sorted elements. -<!-- Generated from commit: b51391b96ee15458ac9cce4b58fb4c5136b02243 --> \ No newline at end of file +<!-- topics: reference-education, data-visualization --> +<!-- Generated from commit: b51391b96ee15458ac9cce4b58fb4c5136b02243 --> diff --git a/species-observation-map.docs.md b/species-observation-map.docs.md index 2cebc50e..bdff0ca1 100644 --- a/species-observation-map.docs.md +++ b/species-observation-map.docs.md @@ -2,4 +2,6 @@ Explore wildlife observations on an interactive map by searching for any species and viewing recent sightings from the iNaturalist community. The map displays geotagged observations within a customizable time range, with clustering for easy navigation across regions and detailed information for each sighting including photos, dates, and observer information. Share specific searches through URL bookmarks to quickly return to previous species and time period filters. -<!-- Generated from commit: b875298190a9bc44bef93ad2cb01ef18f4e7027e --> \ No newline at end of file +<!-- topics: maps-geo --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: b875298190a9bc44bef93ad2cb01ef18f4e7027e --> diff --git a/speech-synthesis.docs.md b/speech-synthesis.docs.md index fd143e77..8641ad48 100644 --- a/speech-synthesis.docs.md +++ b/speech-synthesis.docs.md @@ -1,3 +1,5 @@ Test the Web Speech API's speech synthesis capabilities by entering text and configuring voice parameters such as rate, pitch, and volume. The application provides a selection of available system voices and displays real-time status updates as text is being spoken. Users can adjust synthesis settings and stop playback at any time using the intuitive control interface. -<!-- Generated from commit: 811408d27e9e94e432ac8048192fd3b834b36224 --> \ No newline at end of file +<!-- topics: audio-video, reference-education --> +<!-- features: speech --> +<!-- Generated from commit: 811408d27e9e94e432ac8048192fd3b834b36224 --> diff --git a/sql-pretty-printer.docs.md b/sql-pretty-printer.docs.md index d2f9bd6b..c2460b87 100644 --- a/sql-pretty-printer.docs.md +++ b/sql-pretty-printer.docs.md @@ -1,3 +1,5 @@ Format and beautify SQL queries with customizable styling options. This tool supports multiple SQL dialects including SQLite, PostgreSQL, and MySQL, allowing you to control indentation width, keyword capitalization, and indentation style. The formatted output can be easily copied to your clipboard with a single click. -<!-- Generated from commit: 71a762dfc7190f764785b6246e8e17f4fa9a8ecd --> \ No newline at end of file +<!-- topics: developer-tools, sqlite-databases --> +<!-- features: clipboard --> +<!-- Generated from commit: 71a762dfc7190f764785b6246e8e17f4fa9a8ecd --> diff --git a/sqlite-ast.docs.md b/sqlite-ast.docs.md index 8d91ae52..492a3420 100644 --- a/sqlite-ast.docs.md +++ b/sqlite-ast.docs.md @@ -1,3 +1,5 @@ Parse SQLite SELECT queries into abstract syntax trees and view the results in JSON and Python representations. This tool uses the sqlite-ast library running in your browser via Pyodide to analyze SQL syntax and display both the dictionary-based parse tree and a rich pretty-printed representation. It supports complex queries including compound selects, common table expressions, and window functions, and can display partial parse results when encountering syntax errors. -<!-- Generated from commit: 763e22bf8457c261a33c9a54e32322c6436d3faf --> \ No newline at end of file +<!-- topics: sqlite-databases, developer-tools --> +<!-- features: webassembly --> +<!-- Generated from commit: 763e22bf8457c261a33c9a54e32322c6436d3faf --> diff --git a/sqlite-bytecode-explorer.docs.md b/sqlite-bytecode-explorer.docs.md index 79846528..e8a05b80 100644 --- a/sqlite-bytecode-explorer.docs.md +++ b/sqlite-bytecode-explorer.docs.md @@ -1,3 +1,5 @@ Explore SQLite's Virtual Database Engine (VDBE) by analyzing the bytecode that SQLite generates when compiling SQL queries. This tool runs the `EXPLAIN` command on your SQL statements and annotates each instruction with detailed explanations of what it does, from cursor management and table scans to index lookups and aggregate functions. Use it to understand query execution strategies, identify optimization opportunities, and learn how SQLite's register-based virtual machine transforms SQL into low-level operations. -<!-- Generated from commit: f1c84e9a1090b22667a95d19b5ac774ac903b1b1 --> \ No newline at end of file +<!-- topics: sqlite-databases, developer-tools, reference-education --> +<!-- features: webassembly --> +<!-- Generated from commit: f1c84e9a1090b22667a95d19b5ac774ac903b1b1 --> diff --git a/sqlite-qrf.docs.md b/sqlite-qrf.docs.md index 47450da3..e772ff62 100644 --- a/sqlite-qrf.docs.md +++ b/sqlite-qrf.docs.md @@ -1,3 +1,5 @@ Format SQLite query results in 20 different styles including box-drawing tables, CSV, JSON, HTML, Markdown, and more using this interactive WebAssembly-based demonstration. Adjust formatting options like column headers, screen width, NULL display values, and border styles in real-time to see how your SQL queries render across all available output modes. The demo database includes sample tables for employees, products, and orders with pre-built example queries showcasing each formatting style. -<!-- Generated from commit: 94e4ddcc9b5fba8e6f714904dfb6ce4816e9d439 --> \ No newline at end of file +<!-- topics: sqlite-databases, developer-tools --> +<!-- features: webassembly, clipboard, url-state --> +<!-- Generated from commit: 94e4ddcc9b5fba8e6f714904dfb6ce4816e9d439 --> diff --git a/sqlite-wasm.docs.md b/sqlite-wasm.docs.md index 87e203b7..dd1fd8e5 100644 --- a/sqlite-wasm.docs.md +++ b/sqlite-wasm.docs.md @@ -1,3 +1,5 @@ Query pelican sighting records from Half Moon Bay using SQL commands against an in-browser SQLite database. The tool loads sample data containing observations of various pelican species across local beaches with dates, locations, and counts. Enter any valid SQL query in the textarea and execute it to retrieve and view the results in a formatted table. -<!-- Generated from commit: 95211145625db573557d5fb279f4ebeaaf985303 --> \ No newline at end of file +<!-- topics: sqlite-databases --> +<!-- features: webassembly --> +<!-- Generated from commit: 95211145625db573557d5fb279f4ebeaaf985303 --> diff --git a/svg-progressive-render.docs.md b/svg-progressive-render.docs.md index 61056c11..5bac7eb1 100644 --- a/svg-progressive-render.docs.md +++ b/svg-progressive-render.docs.md @@ -1,3 +1,5 @@ View SVG content being progressively rendered character by character over a specified duration. Paste an SVG file into the input field, set the animation duration in seconds, and click Render to watch the image draw itself incrementally while the live editor displays the growing SVG code. The tool automatically completes partial SVG markup to ensure valid rendering at each animation step. -<!-- Generated from commit: ba6a1be46cd42730f6e967e38dd26fe69d470f0c --> \ No newline at end of file +<!-- topics: images-graphics, reference-education --> +<!-- features: svg, fetch-network --> +<!-- Generated from commit: ba6a1be46cd42730f6e967e38dd26fe69d470f0c --> diff --git a/svg-render.docs.md b/svg-render.docs.md index 0e324bab..1aca66cc 100644 --- a/svg-render.docs.md +++ b/svg-render.docs.md @@ -1,3 +1,5 @@ Convert SVG images to JPEG or PNG format with customizable dimensions, padding, and background colors. The tool allows you to paste SVG code directly, upload SVG files via drag-and-drop, or load SVG images from URLs, then instantly previews the converted result and provides download and base64 embedding options. URL hashes preserve your work for easy sharing and recovery. -<!-- Generated from commit: aa44951cdb23b63465877c5f7787f09c83874276 --> \ No newline at end of file +<!-- topics: images-graphics, developer-tools --> +<!-- features: svg, canvas, file-upload, drag-and-drop, url-state, clipboard --> +<!-- Generated from commit: aa44951cdb23b63465877c5f7787f09c83874276 --> diff --git a/svg-sandbox.docs.md b/svg-sandbox.docs.md index c8e5f084..b3c214c1 100644 --- a/svg-sandbox.docs.md +++ b/svg-sandbox.docs.md @@ -1,3 +1,5 @@ Embed SVG images directly into HTML using base64 data URIs, which eliminates the need for separate image files and reduces HTTP requests. This demo showcases three different SVG examples encoded in base64 format and displayed through standard image tags, with included JavaScript that safely decodes and displays the underlying SVG source code. When SVGs are embedded this way as images, any potentially unsafe JavaScript or interactive elements within them are automatically ignored by the browser, providing a secure method for inline image delivery. -<!-- Generated from commit: a7289c8e90d5ab339e78812479982bf02cc64e6b --> \ No newline at end of file +<!-- topics: images-graphics, reference-education --> +<!-- features: svg --> +<!-- Generated from commit: a7289c8e90d5ab339e78812479982bf02cc64e6b --> diff --git a/swagger-subset.docs.md b/swagger-subset.docs.md index 8659a512..6142dc47 100644 --- a/swagger-subset.docs.md +++ b/swagger-subset.docs.md @@ -1,3 +1,5 @@ Extract a subset of Swagger/OpenAPI definitions by selecting specific API endpoints and their dependencies. This tool parses a Swagger JSON document, displays all available paths and methods in an interactive checklist, and generates a filtered JSON output containing only the selected endpoints along with any referenced schema definitions they require. The generated subset can be copied to the clipboard for use in other applications or documentation. -<!-- Generated from commit: 49277989809c8b6ca92e82ff82765d634b8400b2 --> \ No newline at end of file +<!-- topics: developer-tools, data-json --> +<!-- features: clipboard --> +<!-- Generated from commit: 49277989809c8b6ca92e82ff82765d634b8400b2 --> diff --git a/syntaqlite.docs.md b/syntaqlite.docs.md index e46bcba4..98daf1ed 100644 --- a/syntaqlite.docs.md +++ b/syntaqlite.docs.md @@ -2,4 +2,6 @@ Experiment with SQLite SQL parsing, formatting, validation, and tokenization directly in your browser using the syntaqlite parser. This interactive playground provides four main tools: a code formatter that restructures SQL with customizable options, a parser that generates abstract syntax trees, a validator that checks queries against a defined schema, and a tokenizer that breaks SQL into individual tokens with type classification. All processing happens client-side via Pyodide, which runs Python code in WebAssembly without requiring any server infrastructure. -<!-- Generated from commit: d64e3f4d156aa46443e3ba886ed934416dbc1118 --> \ No newline at end of file +<!-- topics: sqlite-databases, developer-tools --> +<!-- features: webassembly --> +<!-- Generated from commit: d64e3f4d156aa46443e3ba886ed934416dbc1118 --> diff --git a/tacopy-playground.docs.md b/tacopy-playground.docs.md index 29b0e63e..17113464 100644 --- a/tacopy-playground.docs.md +++ b/tacopy-playground.docs.md @@ -1,3 +1,5 @@ Explore how tail-recursive Python functions are transformed into optimized iterative code using the Tacopy library. Enter your recursive function in the input panel to see the automatically generated transformed version, which eliminates stack overflow risks and improves performance by converting tail calls into loops. Try the built-in examples to understand how different recursive patterns are optimized. -<!-- Generated from commit: 3af1ed845e36cfa53a161b3ce33406872057b9ea --> \ No newline at end of file +<!-- topics: developer-tools, reference-education --> +<!-- features: webassembly --> +<!-- Generated from commit: 3af1ed845e36cfa53a161b3ce33406872057b9ea --> diff --git a/tags.json b/tags.json index 2908739b..3f7f42c1 100644 --- a/tags.json +++ b/tags.json @@ -40,6 +40,7 @@ "fullscreen": "Fullscreen", "notifications": "Notifications", "web-share": "Web Share", - "url-state": "URL State" + "url-state": "URL State", + "web-serial": "Web Serial" } } diff --git a/terminal-to-html.docs.md b/terminal-to-html.docs.md index 89e81916..e9c4da82 100644 --- a/terminal-to-html.docs.md +++ b/terminal-to-html.docs.md @@ -1,3 +1,5 @@ Convert terminal output into shareable HTML documents with support for colored text formatting. Paste terminal output in RTF, HTML, or plain text format, and the tool instantly generates clean HTML code ready for preview or export. Save your conversions as GitHub Gists for easy sharing and collaboration. -<!-- Generated from commit: 7b7a04fc224bbe0cec3fc00ce755273c2d6ae11d --> \ No newline at end of file +<!-- topics: developer-tools, text-writing --> +<!-- features: clipboard, local-storage, fetch-network --> +<!-- Generated from commit: 7b7a04fc224bbe0cec3fc00ce755273c2d6ae11d --> diff --git a/text-diff.docs.md b/text-diff.docs.md index 57df3708..5c7a60a4 100644 --- a/text-diff.docs.md +++ b/text-diff.docs.md @@ -1,3 +1,4 @@ Compare two blocks of text to identify character-level differences between them. This tool uses a dynamic programming algorithm to compute the longest common subsequence and highlights removed text in red and added text in green for easy visualization of changes. The results are displayed character-by-character in a dedicated output section that clearly indicates what was deleted from the original text and what was inserted in the modified version. -<!-- Generated from commit: b3c628b84c5c6a3b7fcfff10aa5de98b7f5d6962 --> \ No newline at end of file +<!-- topics: text-writing, developer-tools --> +<!-- Generated from commit: b3c628b84c5c6a3b7fcfff10aa5de98b7f5d6962 --> diff --git a/text-indentation.docs.md b/text-indentation.docs.md index 19b6394b..dcd8ac78 100644 --- a/text-indentation.docs.md +++ b/text-indentation.docs.md @@ -1,3 +1,5 @@ Adjust indentation levels in your text with this tool that offers multiple formatting options. Add or remove spaces from the beginning of each line, strip all leading whitespace, eliminate trailing spaces, and apply or remove quote markers (>) for formatted text. Copy the processed result directly to your clipboard with a single click. -<!-- Generated from commit: 42c83ef2843c8e5d1645b3921b8ee05a1a81bbea --> \ No newline at end of file +<!-- topics: text-writing, productivity --> +<!-- features: clipboard --> +<!-- Generated from commit: 42c83ef2843c8e5d1645b3921b8ee05a1a81bbea --> diff --git a/text-wrap-balance-nav.docs.md b/text-wrap-balance-nav.docs.md index 6686c88b..6d084e5f 100644 --- a/text-wrap-balance-nav.docs.md +++ b/text-wrap-balance-nav.docs.md @@ -1,3 +1,4 @@ Explore how the CSS `text-wrap: balance` property affects navigation layout and text distribution across multiple lines. This interactive demonstration allows you to toggle the text-wrap balance feature on and off while adjusting the number of visible navigation items to see how the browser distributes text more evenly across lines. Use the slider and checkbox controls to observe the differences in how links wrap and align within the constrained navigation container. -<!-- Generated from commit: 2c59da733016245fedb2f9fc4236a3a334059c01 --> \ No newline at end of file +<!-- topics: css-layout, reference-education --> +<!-- Generated from commit: 2c59da733016245fedb2f9fc4236a3a334059c01 --> diff --git a/tiff-orientation.docs.md b/tiff-orientation.docs.md index cdc4dfce..66ef4a62 100644 --- a/tiff-orientation.docs.md +++ b/tiff-orientation.docs.md @@ -1,3 +1,5 @@ Read TIFF orientation metadata from JPEG images by uploading or dragging files into the drop zone. The tool parses the EXIF data embedded in the image file to extract the orientation tag, which indicates how the image should be displayed (normal, rotated 90° clockwise, rotated 180°, or rotated 270° clockwise). Debug information shows the file analysis process, including EXIF location, endianness detection, and TIFF header validation. -<!-- Generated from commit: 9b6cdd52381f1acf2c1148ed23478da1ce1f199f --> \ No newline at end of file +<!-- topics: images-graphics, developer-tools --> +<!-- features: file-upload, drag-and-drop --> +<!-- Generated from commit: 9b6cdd52381f1acf2c1148ed23478da1ce1f199f --> diff --git a/timezones.docs.md b/timezones.docs.md index 57c8c09e..ecf4384a 100644 --- a/timezones.docs.md +++ b/timezones.docs.md @@ -1,3 +1,5 @@ Plan meetings across multiple time zones by selecting two locations and viewing their local times side-by-side. The comparison table displays 48 consecutive hours of UTC times with corresponding local times for each timezone, making it easy to identify overlapping working hours. Your timezone selections are automatically saved in the URL for convenient sharing and bookmarking. -<!-- Generated from commit: a1420370ae38120819da3ddbb6fcefe1d9844f77 --> \ No newline at end of file +<!-- topics: productivity --> +<!-- features: url-state --> +<!-- Generated from commit: a1420370ae38120819da3ddbb6fcefe1d9844f77 --> diff --git a/token-usage.docs.md b/token-usage.docs.md index 4f1decb7..4aee8a8d 100644 --- a/token-usage.docs.md +++ b/token-usage.docs.md @@ -1,3 +1,4 @@ Calculate token usage across your Claude and other LLM API calls by pasting YAML output from the LLM tool's `llm logs -su` command. The calculator automatically groups token consumption by model and displays total input and output tokens for each. This helps you track and analyze API usage patterns across multiple conversations and model versions. -<!-- Generated from commit: 330106eb4f9fd2b4db6ca48c8b520445f62797ba --> \ No newline at end of file +<!-- topics: ai-llm, productivity --> +<!-- Generated from commit: 330106eb4f9fd2b4db6ca48c8b520445f62797ba --> diff --git a/transfer-time.docs.md b/transfer-time.docs.md index 52c5b7aa..b334781e 100644 --- a/transfer-time.docs.md +++ b/transfer-time.docs.md @@ -1,3 +1,4 @@ Calculate file transfer duration by entering the file size and transfer speed with their respective units. The calculator automatically converts between different measurement units (GB, MB, TB for file size; Mbps, MB/s, KB/s for speed) and displays the estimated transfer time in an easily readable format. Results include a detailed breakdown showing days, hours, minutes, and seconds alongside the calculation parameters. -<!-- Generated from commit: f03108dda0d57ce10ffde79f1e148619eaa0e28e --> \ No newline at end of file +<!-- topics: productivity --> +<!-- Generated from commit: f03108dda0d57ce10ffde79f1e148619eaa0e28e --> diff --git a/transparent-png.docs.md b/transparent-png.docs.md index 2b38b26f..642843be 100644 --- a/transparent-png.docs.md +++ b/transparent-png.docs.md @@ -2,4 +2,6 @@ Make Colors Transparent in PNG is an interactive tool that allows you to remove specific colors from images and export the result with transparent backgrounds. Upload or paste an image, click on any color to select it for transparency, and adjust the tolerance slider to control how many similar colors are removed. Download your processed image as a PNG file with the ability to preview the result against different background colors. -<!-- Generated from commit: 38655b7ce7194379712102053edf737dd5fa2c87 --> \ No newline at end of file +<!-- topics: images-graphics --> +<!-- features: canvas, file-upload, drag-and-drop, clipboard --> +<!-- Generated from commit: 38655b7ce7194379712102053edf737dd5fa2c87 --> diff --git a/turbo-pascal-deconstructed.docs.md b/turbo-pascal-deconstructed.docs.md index 9dab86d3..dd4d486e 100644 --- a/turbo-pascal-deconstructed.docs.md +++ b/turbo-pascal-deconstructed.docs.md @@ -1,3 +1,4 @@ Explore an interactive breakdown of Turbo Pascal 3.02A's 39,731-byte executable, mapping each function from the header and display system through the parser and symbol table. Navigate the binary segments with an overhead visualization and detailed hex dumps with annotated disassembly, revealing how a complete compiler, editor, and runtime fit within the constraints of 1986 DOS memory while routing all file I/O through a single INT 21h dispatcher gateway. -<!-- Generated from commit: b0e0ad77b9ac19eb0074f122fbb7f41e67b941ae --> \ No newline at end of file +<!-- topics: reference-education, developer-tools --> +<!-- Generated from commit: b0e0ad77b9ac19eb0074f122fbb7f41e67b941ae --> diff --git a/unicode-binary-search.docs.md b/unicode-binary-search.docs.md index 72ad9ef5..2acf54e2 100644 --- a/unicode-binary-search.docs.md +++ b/unicode-binary-search.docs.md @@ -1,3 +1,5 @@ View Unicode characters and their properties through an interactive binary search algorithm that makes real HTTP Range requests to fetch individual records from a binary database. Enter a character or Unicode codepoint to see each step of the search visualized in a network log, including fetch times and comparisons. The tool supports both standard binary search and interpolation search, which estimates the target's position based on codepoint values rather than always splitting the middle, potentially reducing the number of network requests needed. -<!-- Generated from commit: 0beead964c12f300b6484a0126cb89cfe928a2ee --> \ No newline at end of file +<!-- topics: reference-education, developer-tools --> +<!-- features: fetch-network --> +<!-- Generated from commit: 0beead964c12f300b6484a0126cb89cfe928a2ee --> diff --git a/unix-timestamp.docs.md b/unix-timestamp.docs.md index 1e79dcd3..039bb251 100644 --- a/unix-timestamp.docs.md +++ b/unix-timestamp.docs.md @@ -1,3 +1,4 @@ Convert Unix timestamps to human-readable dates and times with this tool. Enter a Unix timestamp (in seconds or milliseconds) to instantly view the corresponding date and time in both UTC and your local timezone. The converter automatically handles both 10-digit and 13-digit timestamps, making it easy to work with timestamps from various sources and systems. -<!-- Generated from commit: 9c103673bb7d2f393911d7f81cfc29c16d160b53 --> \ No newline at end of file +<!-- topics: developer-tools, productivity --> +<!-- Generated from commit: 9c103673bb7d2f393911d7f81cfc29c16d160b53 --> diff --git a/usborne-mad-house.docs.md b/usborne-mad-house.docs.md index 876b4752..4d865c0e 100644 --- a/usborne-mad-house.docs.md +++ b/usborne-mad-house.docs.md @@ -1,3 +1,4 @@ Play a retro text-based escape game inspired by 1980s Usborne computer books, where you control doorways in a shifting house to align three exits before footsteps catch you. Use keyboard controls (X/C and N/M) or on-screen buttons to move the near and far doorways left and right, while the center doorway moves unpredictably. The game features authentic CRT phosphor aesthetics with scanlines and a pulsing HUD that tracks your remaining time and door alignment status. -<!-- Generated from commit: e065e40e78ce21d7ae5b012d24bb35330c1f3180 --> \ No newline at end of file +<!-- topics: games-fun --> +<!-- Generated from commit: e065e40e78ce21d7ae5b012d24bb35330c1f3180 --> diff --git a/user-agent.docs.md b/user-agent.docs.md index 49537052..3f7bb0a3 100644 --- a/user-agent.docs.md +++ b/user-agent.docs.md @@ -1,3 +1,4 @@ Display your browser's user agent string, which contains information about your web browser, operating system, and device. This identifier is sent with every HTTP request your browser makes and helps websites understand how to optimize their content for your specific platform and browser version. -<!-- Generated from commit: d053b9472344ce4c6b2b3c101cb305bd15781ba2 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- Generated from commit: d053b9472344ce4c6b2b3c101cb305bd15781ba2 --> diff --git a/v86.docs.md b/v86.docs.md index d6e8bd5a..cfaf82ce 100644 --- a/v86.docs.md +++ b/v86.docs.md @@ -1,3 +1,5 @@ Run Linux commands in your browser using x86 emulation powered by v86, a JavaScript/WebAssembly-based x86 emulator. This tool executes a minimal Buildroot Linux distribution directly in your browser, with typical boot times between 10-30 seconds depending on your device and connection speed. Enter commands in the input field to interact with the Linux shell and view output in the terminal window. -<!-- Generated from commit: e8a68e36c67b2969215d9184ccba2b446c2f5314 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: webassembly, canvas --> +<!-- Generated from commit: e8a68e36c67b2969215d9184ccba2b446c2f5314 --> diff --git a/view-pdf.docs.md b/view-pdf.docs.md index 19719318..c11a2a93 100644 --- a/view-pdf.docs.md +++ b/view-pdf.docs.md @@ -1,3 +1,5 @@ View PDF files from any CORS-enabled URL with this interactive PDF viewer application. The viewer supports navigation between pages, adjustable zoom levels including auto-scaling, and maintains your viewing state through URL parameters. High-DPI display support ensures sharp text rendering across all devices, and the responsive design adapts seamlessly to mobile screens. -<!-- Generated from commit: 8d8bac810dc3a0b4b1b3a2ff37a1d2c412b222e0 --> \ No newline at end of file +<!-- topics: documents-pdf --> +<!-- features: canvas, fetch-network, url-state --> +<!-- Generated from commit: 8d8bac810dc3a0b4b1b3a2ff37a1d2c412b222e0 --> diff --git a/visualizer.docs.md b/visualizer.docs.md index 0746e6db..f87fe2ad 100644 --- a/visualizer.docs.md +++ b/visualizer.docs.md @@ -1,3 +1,5 @@ Create real-time audio-reactive visualizations with eight distinct modes including plasma, particles, tunnel effects, kaleidoscope patterns, Matrix rain, terrain, fire, and starfield animations. The visualizer captures frequency data from your microphone and responds dynamically to bass, mid, and high frequencies, with beat detection triggering visual flashes and intensity changes. Sequence mode automatically cycles through all visualization styles with smooth transitions, while fullscreen capability allows for immersive display on any screen. -<!-- Generated from commit: bf3c8537cf1236df1be6fb48ec6600bbf50dd2b3 --> \ No newline at end of file +<!-- topics: audio-video, data-visualization --> +<!-- features: canvas, web-audio, camera-mic, fullscreen --> +<!-- Generated from commit: bf3c8537cf1236df1be6fb48ec6600bbf50dd2b3 --> diff --git a/webkitdirectory.docs.md b/webkitdirectory.docs.md index 119f147a..80ebd841 100644 --- a/webkitdirectory.docs.md +++ b/webkitdirectory.docs.md @@ -1,3 +1,5 @@ Explore the contents of a local directory in your browser with an interactive file tree viewer and search functionality. This tool demonstrates the capabilities of the `webkitdirectory` input attribute to access folder structures and analyze file distribution. Once a directory is selected, view detailed statistics about file counts, total size, and file type breakdown, with options to filter by name and file extension. -<!-- Generated from commit: e6b8a4661f03ee58feeb8eddc40145823e596019 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: file-upload, drag-and-drop --> +<!-- Generated from commit: e6b8a4661f03ee58feeb8eddc40145823e596019 --> diff --git a/wikipedia-wikitext.docs.md b/wikipedia-wikitext.docs.md index a1bfb17d..bd717904 100644 --- a/wikipedia-wikitext.docs.md +++ b/wikipedia-wikitext.docs.md @@ -1,3 +1,5 @@ Retrieve the raw wikitext source code from Wikipedia articles by searching for a page title or pasting a direct article URL. The tool features autocomplete suggestions while typing search queries and allows you to easily copy the fetched wikitext to your clipboard for further editing or analysis. URL parameters are preserved, enabling you to share links that automatically load specific Wikipedia articles. -<!-- Generated from commit: 675d8d5ef2bc69c06d552d06ef3a63c8238b2244 --> \ No newline at end of file +<!-- topics: reference-education --> +<!-- features: fetch-network, clipboard, url-state --> +<!-- Generated from commit: 675d8d5ef2bc69c06d552d06ef3a63c8238b2244 --> diff --git a/word-counter.docs.md b/word-counter.docs.md index 1db3df01..836410b5 100644 --- a/word-counter.docs.md +++ b/word-counter.docs.md @@ -1,3 +1,5 @@ Track word and character counts across multiple writing sections with automatic saving to browser storage. Each section displays real-time statistics as you type, and content persists between sessions. Add or remove writing sections as needed to organize different pieces of text. -<!-- Generated from commit: cb33238bc7a9029e6453052184287dc8b1679f92 --> \ No newline at end of file +<!-- topics: text-writing, productivity --> +<!-- features: local-storage --> +<!-- Generated from commit: cb33238bc7a9029e6453052184287dc8b1679f92 --> diff --git a/writing-style.docs.md b/writing-style.docs.md index 9024dd72..c7f16c71 100644 --- a/writing-style.docs.md +++ b/writing-style.docs.md @@ -1,3 +1,4 @@ Analyze your writing for common style issues by pasting text into this tool, which detects weasel words (such as "very" and "quite"), passive voice constructions, and duplicate consecutive words. The analyzer provides contextual snippets for each issue found, helping you identify areas where your writing could be more direct and concise. This tool is adapted from shell scripts by Matt Might and updates results in real-time as you type. -<!-- Generated from commit: 0fbf511ab06b62a9fe8061198b90904aab111e93 --> \ No newline at end of file +<!-- topics: text-writing --> +<!-- Generated from commit: 0fbf511ab06b62a9fe8061198b90904aab111e93 --> diff --git a/xml-validator.docs.md b/xml-validator.docs.md index 8b2c0294..28ba65d7 100644 --- a/xml-validator.docs.md +++ b/xml-validator.docs.md @@ -1,3 +1,4 @@ Check XML documents for well-formedness by pasting content into the input area and clicking the validate button. The tool parses the XML and displays any syntax errors with precise line and column information, highlighting the problematic line in the code view below. -<!-- Generated from commit: 8c49c1a81f9cf0673bcd8d20c30fc929c18909b6 --> \ No newline at end of file +<!-- topics: developer-tools, data-json --> +<!-- Generated from commit: 8c49c1a81f9cf0673bcd8d20c30fc929c18909b6 --> diff --git a/yaml-explorer.docs.md b/yaml-explorer.docs.md index 368d74a9..1517127e 100644 --- a/yaml-explorer.docs.md +++ b/yaml-explorer.docs.md @@ -1,3 +1,5 @@ Parse and visualize YAML files in an interactive tree format with collapsible sections for easy navigation of nested data structures. Enter YAML content directly or load from a URL, then explore the data by expanding and collapsing individual elements. The tool preserves your navigation state in the URL, allowing you to share links with specific sections already expanded. -<!-- Generated from commit: ee48769f1bf8e56cad82db5a9207ca668f291162 --> \ No newline at end of file +<!-- topics: data-json, developer-tools --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: ee48769f1bf8e56cad82db5a9207ca668f291162 --> diff --git a/youtube-thumbnails.docs.md b/youtube-thumbnails.docs.md index 1f1a1c6f..e65d5056 100644 --- a/youtube-thumbnails.docs.md +++ b/youtube-thumbnails.docs.md @@ -1,3 +1,5 @@ View YouTube video thumbnails in multiple resolutions by entering a video URL or ID. This tool extracts and displays all available thumbnail formats from YouTube's image server, allowing you to preview different quality options and copy direct image links. Click on any thumbnail to expand it for a closer look, and use the copy button to save the image URL to your clipboard. -<!-- Generated from commit: 8d67d6ca349fdb27f0287cfd388b9a5485cd88b5 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: clipboard, url-state --> +<!-- Generated from commit: 8d67d6ca349fdb27f0287cfd388b9a5485cd88b5 --> diff --git a/zip-wheel-explorer.docs.md b/zip-wheel-explorer.docs.md index cc9b33b1..dc773a6e 100644 --- a/zip-wheel-explorer.docs.md +++ b/zip-wheel-explorer.docs.md @@ -1,3 +1,5 @@ Browse and view the contents of Python package files (.whl and .zip archives) directly in your browser by entering a PyPI package name or a direct file URL. The tool automatically downloads the package, extracts all files, and displays them in an interactive list with syntax highlighting and line-by-line navigation. You can link directly to specific files and lines using URL fragments for easy sharing. -<!-- Generated from commit: 207d2955d806e5533fe81f7b53428f5425883fc3 --> \ No newline at end of file +<!-- topics: developer-tools --> +<!-- features: fetch-network, url-state --> +<!-- Generated from commit: 207d2955d806e5533fe81f7b53428f5425883fc3 --> From bca94957023bb3e1580ade6bd3edfa73716b1859 Mon Sep 17 00:00:00 2001 From: Jesse Vincent <jesse@fsck.com> Date: Fri, 5 Jun 2026 15:20:43 -0700 Subject: [PATCH 3/7] Render Yahoo-style tag directory on the homepage directory.py groups every tool by topic and by browser feature into a classic directory layout; build_index.py injects it below the recent section with retro styling and anchor-linked feature chips. --- build_index.py | 100 +++++++++++++++++++++++++++++++++++++++++++++- directory.py | 79 ++++++++++++++++++++++++++++++++++++ test_directory.py | 74 ++++++++++++++++++++++++++++++++++ 3 files changed, 252 insertions(+), 1 deletion(-) create mode 100644 directory.py create mode 100644 test_directory.py diff --git a/build_index.py b/build_index.py index 44b18030..30c306fa 100755 --- a/build_index.py +++ b/build_index.py @@ -8,6 +8,9 @@ from pathlib import Path from typing import Iterable, List, Sequence +import directory +import tags_lib + try: import markdown except ModuleNotFoundError as exc: # pragma: no cover - dependency should be installed @@ -158,7 +161,11 @@ def build_index() -> None: recent_section_html = _render_recent_section(recently_added, recently_updated) - # Inject the recent section between the comment markers + vocab = tags_lib.load_vocabulary() + directory_html = directory.render_directory(tools, vocab) + + # Inject the recent section between the comment markers, then the directory + # immediately after the closing marker. start_marker = '<!-- recently starts -->' end_marker = '<!-- recently stops -->' if start_marker in body_html and end_marker in body_html: @@ -171,6 +178,9 @@ def build_index() -> None: '\n' + recent_section_html + body_html[end_idx:] ) + body_html = body_html.replace( + end_marker, end_marker + '\n' + directory_html, 1 + ) else: # Fallback: inject before Image and media heading if markers not found injection_marker = '<h2 id="image-and-media">Image and media</h2>' @@ -180,6 +190,7 @@ def build_index() -> None: ) else: body_html = recent_section_html + body_html + body_html = body_html + '\n' + directory_html full_html = f"""<!DOCTYPE html> <html lang="en"> @@ -334,6 +345,93 @@ def build_index() -> None: font-size: 0.9em; margin-top: 0.5em; }} + html {{ + scroll-behavior: smooth; + }} + .directory {{ + margin-top: 2.5em; + border-top: 3px double #9a67af; + padding-top: 1em; + }} + .dir-intro {{ + color: #444; + font-size: 0.95em; + max-width: 48em; + margin: 0.5em 0 1em; + }} + .dir-heading {{ + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.35em; + color: #4a2f63; + border-bottom: 2px solid #9a67af; + padding-bottom: 2px; + margin: 1.4em 0 0.8em; + }} + .dir-chips {{ + display: flex; + flex-wrap: wrap; + gap: 6px; + margin: 0 0 1.5em; + }} + .dir-chip {{ + font-size: 0.82em; + background: #f0ebf5; + border: 1px solid #d3c4e0; + border-radius: 3px; + padding: 2px 8px; + color: #5a3d73 !important; + white-space: nowrap; + }} + .dir-chip:hover {{ + background: #5a3d73; + color: #fff !important; + text-decoration: none; + }} + .dir-grid {{ + column-width: 280px; + column-gap: 30px; + }} + .dir-cat {{ + break-inside: avoid; + -webkit-column-break-inside: avoid; + display: inline-block; + width: 100%; + margin: 0 0 1.4em; + vertical-align: top; + }} + .dir-cat h3 {{ + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.05em; + font-weight: bold; + margin: 0 0 0.3em; + padding-bottom: 2px; + border-bottom: 1px solid #c9b8d6; + color: #5a3d73; + }} + .dir-cat ul {{ + list-style: none; + margin: 0; + padding: 0; + }} + .dir-cat li {{ + font-size: 0.9em; + line-height: 1.5; + padding-left: 0.9em; + text-indent: -0.9em; + }} + .dir-cat li::before {{ + content: "\\203A"; + color: #b8a3c9; + margin-right: 0.4em; + }} + .dir-count {{ + color: #999; + font-weight: normal; + font-size: 0.85em; + }} + :target > h3 {{ + background: #fdf6a8; + }} </style> </head> <body> diff --git a/directory.py b/directory.py new file mode 100644 index 00000000..b179e5ae --- /dev/null +++ b/directory.py @@ -0,0 +1,79 @@ +"""Render a classic Yahoo-style directory of tools grouped by tag. + +Produces a static HTML fragment: tools grouped by topic ("what it does") and a +second grouping by browser feature. Output works with no JavaScript; the +homepage progressively enhances it with feature-filter chips. +""" + +from __future__ import annotations + +import html +from typing import Dict, List, Sequence + + +def _group(tools: Sequence[dict], namespace: str, vocab_group: Dict[str, str]): + """Yield ``(slug, display_name, [tools])`` for each non-empty tag, in vocab order.""" + buckets: Dict[str, List[dict]] = {slug: [] for slug in vocab_group} + for tool in tools: + for tag in tool.get(namespace, []): + buckets.setdefault(tag, []).append(tool) + + ordered = list(vocab_group) + [slug for slug in buckets if slug not in vocab_group] + for slug in ordered: + members = buckets.get(slug) + if not members: + continue + display = vocab_group.get(slug, slug.replace("-", " ").title()) + members = sorted(members, key=lambda t: t.get("title", "").lower()) + yield slug, display, members + + +def _render_section(title: str, anchor_prefix: str, groups) -> str: + blocks = [] + for slug, display, members in groups: + anchor = f"{anchor_prefix}-{slug}" + links = "\n".join( + f' <li><a href="{html.escape(tool.get("url", "#"))}">' + f'{html.escape(tool.get("title", tool.get("slug", "")))}</a></li>' + for tool in members + ) + blocks.append( + f""" <div class="dir-cat" id="{html.escape(anchor)}"> + <h3>{html.escape(display)} <span class="dir-count">({len(members)})</span></h3> + <ul> +{links} + </ul> + </div>""" + ) + return ( + f'<h2 class="dir-heading">{html.escape(title)}</h2>\n' + f'<div class="dir-grid">\n' + "\n".join(blocks) + "\n</div>" + ) + + +def render_directory(tools: Sequence[dict], vocab: dict) -> str: + """Render the full directory HTML fragment from tools and the tag vocabulary.""" + topic_groups = list(_group(tools, "topics", vocab.get("topics", {}))) + feature_groups = list(_group(tools, "features", vocab.get("features", {}))) + + feature_chips = "\n".join( + f' <a class="dir-chip" href="#feature-{html.escape(slug)}" ' + f'data-feature="{html.escape(slug)}">{html.escape(display)} ' + f'<span class="dir-count">({len(members)})</span></a>' + for slug, display, members in feature_groups + ) + + topics_html = _render_section("Browse by category", "topic", topic_groups) + features_html = _render_section( + "Browse by browser feature", "feature", feature_groups + ) + + return f"""<div class="directory" data-directory> +<p class="dir-intro">A classic directory of every tool, sorted into categories. +Pick a category below, or filter by the browser features a tool uses.</p> +<div class="dir-chips" data-feature-chips> +{feature_chips} +</div> +{topics_html} +{features_html} +</div>""" diff --git a/test_directory.py b/test_directory.py new file mode 100644 index 00000000..2e445007 --- /dev/null +++ b/test_directory.py @@ -0,0 +1,74 @@ +"""Unit tests for the Yahoo-style directory renderer.""" + +import directory + + +VOCAB = { + "topics": {"developer-tools": "Developer Tools", "games-fun": "Games & Fun"}, + "features": {"clipboard": "Clipboard", "canvas": "Canvas"}, +} + +TOOLS = [ + { + "slug": "json-diff", + "title": "JSON Diff Tool", + "url": "/json-diff", + "topics": ["developer-tools"], + "features": ["clipboard"], + }, + { + "slug": "snake", + "title": "Snake Game", + "url": "/snake", + "topics": ["games-fun", "developer-tools"], + "features": ["canvas"], + }, +] + + +def test_groups_tools_under_each_topic(): + html = directory.render_directory(TOOLS, VOCAB) + # developer-tools has both tools; games-fun has one + assert "Developer Tools" in html + assert "Games & Fun" in html or "Games & Fun" in html + # json-diff: 1 topic (developer-tools) + 1 feature (clipboard) + assert html.count('href="/json-diff"') == 2 + # snake: 2 topics (games-fun, developer-tools) + 1 feature (canvas) + assert html.count('href="/snake"') == 3 + + +def test_counts_reflect_membership(): + html = directory.render_directory(TOOLS, VOCAB) + assert "Developer Tools" in html and "(2)" in html + assert "(1)" in html + + +def test_empty_categories_are_omitted(): + vocab = { + "topics": {"developer-tools": "Developer Tools", "maps-geo": "Maps & Geography"}, + "features": {"clipboard": "Clipboard"}, + } + html = directory.render_directory(TOOLS, vocab) + assert "Maps & Geography" not in html and "Maps & Geography" not in html + + +def test_escapes_titles(): + tools = [ + { + "slug": "x", + "title": "A & B <script>", + "url": "/x", + "topics": ["developer-tools"], + "features": [], + } + ] + html = directory.render_directory(tools, VOCAB) + assert "<script>" not in html + assert "A & B" in html + + +def test_feature_section_present(): + html = directory.render_directory(TOOLS, VOCAB) + assert "Browse by browser feature" in html + assert "Clipboard" in html + assert "Canvas" in html From da75529335bcd9221c2db4cb93594919d6626570 Mon Sep 17 00:00:00 2001 From: Jesse Vincent <jesse@fsck.com> Date: Fri, 5 Jun 2026 15:21:47 -0700 Subject: [PATCH 4/7] Persist coined tags: commit tags.json alongside generated docs --- .github/workflows/pages.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index 1b2d7442..7f5012fa 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -64,6 +64,8 @@ jobs: git config user.name "Automated" git config user.email "actions@users.noreply.github.com" git add *.docs.md + # Persist any new tags coined while generating docs + git add tags.json git commit -m "Generated docs: ${{ steps.docs.outputs.stems }}" || exit 0 git push From 20d13893e515ba664d73c88e3f73dd3c91e8b641 Mon Sep 17 00:00:00 2001 From: Jesse Vincent <jesse@fsck.com> Date: Fri, 5 Jun 2026 15:30:55 -0700 Subject: [PATCH 5/7] Carve developer-tools into a category hierarchy - Split the 104-tool developer-tools catch-all: new code-sandboxes (10) and apis-services (16) topics, and drop the redundant developer-tools tag from tools that already have a specific home (104 -> 14 residual). - Restructure tags.json into top-level categories -> subcategories. - directory.py now renders the two-level Yahoo-style hierarchy with a category nav and per-category banners. --- apsw-query.docs.md | 2 +- ares.docs.md | 2 +- badge-drawer.docs.md | 2 +- badge-repl.docs.md | 2 +- base64-gzip-decoder.docs.md | 2 +- bbox-cropper.docs.md | 2 +- bluesky-firehose.docs.md | 2 +- bluesky-resolve.docs.md | 2 +- box-shadow.docs.md | 2 +- broadcast-channel-chat.docs.md | 2 +- bugzilla-bug.docs.md | 2 +- build_index.py | 14 +++ chrome-prompt-playground.docs.md | 2 +- claude-code-timeline.docs.md | 2 +- claude-token-counter.docs.md | 2 +- clipboard-backup.docs.md | 2 +- codex-timeline.docs.md | 2 +- cors-fetch.docs.md | 2 +- csp-allow.docs.md | 2 +- curly-emdash.docs.md | 2 +- deep-research-viewer.docs.md | 2 +- directory.py | 154 ++++++++++++++++++---------- dns.docs.md | 2 +- dot.docs.md | 2 +- emoji-identifier.docs.md | 2 +- escape-entities.docs.md | 2 +- exif.docs.md | 2 +- extract-urls.docs.md | 2 +- ffmpeg-crop.docs.md | 2 +- gif-dissector.docs.md | 2 +- github-account.docs.md | 2 +- github-api-write.docs.md | 2 +- github-graphiql.docs.md | 2 +- github-issue-to-markdown.docs.md | 2 +- github-ratelimit.docs.md | 2 +- github-repo-size.docs.md | 2 +- github-repo-stats.docs.md | 2 +- html-preview.docs.md | 2 +- huggingface-storage.docs.md | 2 +- iframe-resize.docs.md | 2 +- iframe-sandbox.docs.md | 2 +- incomplete-json-printer.docs.md | 2 +- jina-reader.docs.md | 2 +- json-diff.docs.md | 2 +- json-schema-builder.docs.md | 2 +- json-string-extractor.docs.md | 2 +- justhtml.docs.md | 2 +- link-extractor.docs.md | 2 +- manyana.docs.md | 2 +- mask-visualizer.docs.md | 2 +- mdn-timelines.docs.md | 2 +- micropython.docs.md | 2 +- microquickjs.docs.md | 2 +- mp3-inspector.docs.md | 2 +- nav-for-headings.docs.md | 2 +- numpy-pyodide-lab.docs.md | 2 +- passkeys.docs.md | 2 +- paste-html-subset.docs.md | 2 +- paste-rich-text.docs.md | 2 +- php-deserializer.docs.md | 2 +- pretext-explainer.docs.md | 2 +- prompt-caching.docs.md | 2 +- prompts-js.docs.md | 2 +- pyodide-repl.docs.md | 2 +- pypi-changelog.docs.md | 2 +- python-comment-stripper.docs.md | 2 +- python-vulnerability-lookup.docs.md | 2 +- quickjs.docs.md | 2 +- redis-array.docs.md | 2 +- render-claude-citations.docs.md | 2 +- render-markdown.docs.md | 2 +- rtf-to-html.docs.md | 2 +- schema-dsl.docs.md | 2 +- software-heritage-repo.docs.md | 2 +- sql-pretty-printer.docs.md | 2 +- sqlite-ast.docs.md | 2 +- sqlite-bytecode-explorer.docs.md | 2 +- sqlite-qrf.docs.md | 2 +- svg-render.docs.md | 2 +- swagger-subset.docs.md | 2 +- syntaqlite.docs.md | 2 +- tacopy-playground.docs.md | 2 +- tags.json | 29 ++++++ terminal-to-html.docs.md | 2 +- test_directory.py | 93 ++++++++++++----- text-diff.docs.md | 2 +- tiff-orientation.docs.md | 2 +- turbo-pascal-deconstructed.docs.md | 2 +- unicode-binary-search.docs.md | 2 +- unix-timestamp.docs.md | 2 +- v86.docs.md | 2 +- xml-validator.docs.md | 2 +- yaml-explorer.docs.md | 2 +- youtube-thumbnails.docs.md | 2 +- 94 files changed, 303 insertions(+), 167 deletions(-) diff --git a/apsw-query.docs.md b/apsw-query.docs.md index 1be7d42d..66bb9878 100644 --- a/apsw-query.docs.md +++ b/apsw-query.docs.md @@ -1,5 +1,5 @@ Analyze and explain SQLite queries using APSW by entering SQL code and executing it in an in-browser Python environment. The tool provides detailed query analysis including execution plans, expanded SQL, and query information to help understand how SQLite processes your queries. Optional setup SQL can be run before the main query to create tables or initialize data, and parameterized queries are supported through labeled input fields. -<!-- topics: sqlite-databases, developer-tools --> +<!-- topics: sqlite-databases --> <!-- features: webassembly --> <!-- Generated from commit: 0af31729167e3de7f6ac73afd5e5bc03ba3b68fb --> diff --git a/ares.docs.md b/ares.docs.md index ac89a967..e9170208 100644 --- a/ares.docs.md +++ b/ares.docs.md @@ -1,4 +1,4 @@ Convert text to NATO phonetic alphabet equivalents for clear communication in radio, military, and aviation contexts. Enter any combination of letters and numbers, then click the convert button to display the phonetic representation with each character separated by spaces. Spaces in the original text are marked as "(SPACE)" in the output. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education --> <!-- Generated from commit: 9da6f96d4e3c886f1776cdc5b658e47087a279dd --> diff --git a/badge-drawer.docs.md b/badge-drawer.docs.md index 60be37f1..7a227c58 100644 --- a/badge-drawer.docs.md +++ b/badge-drawer.docs.md @@ -2,6 +2,6 @@ Draw pixel art for e-ink badge displays with this web-based canvas editor supporting multiple brush sizes, undo/redo functionality, and real-time black-and-white preview. Export your designs as PNG files or transfer them directly to Badger2040 devices running MicroPython via Web Serial. The editor maintains device-native resolution while offering adjustable zoom levels and includes features like grid overlay, background image loading, and URL-based bookmarking for saving your work. -<!-- topics: images-graphics, developer-tools --> +<!-- topics: images-graphics --> <!-- features: canvas, url-state, file-upload, web-serial --> <!-- Generated from commit: 914fd7c3e36f51e88c6674ffa2d9557f881c8072 --> diff --git a/badge-repl.docs.md b/badge-repl.docs.md index 9233729c..f6b10f54 100644 --- a/badge-repl.docs.md +++ b/badge-repl.docs.md @@ -1,5 +1,5 @@ Interact with a MicroPython device via the Web Serial API to execute Python commands in real-time through a browser-based REPL interface. This tool enables direct communication with compatible microcontroller boards, allowing users to run Python code, query system information, and manage files without requiring terminal software or drivers. The interface provides quick-access buttons for common operations like listing files, checking CPU frequency, and monitoring available memory. -<!-- topics: developer-tools --> +<!-- topics: code-sandboxes --> <!-- features: web-serial --> <!-- Generated from commit: 5cdacf6eb6ce834dd3814386e6860ec22af5fd5d --> diff --git a/base64-gzip-decoder.docs.md b/base64-gzip-decoder.docs.md index 7c25f302..3f9d4276 100644 --- a/base64-gzip-decoder.docs.md +++ b/base64-gzip-decoder.docs.md @@ -1,4 +1,4 @@ Decode base64-encoded gzip data to retrieve the original decompressed content. Paste your base64 string into the input field and click the Decode button to process the data. The decoder handles the conversion from base64 format and gzip decompression in sequence, displaying the result or providing detailed error messages if the input is invalid. -<!-- topics: encoding-security, developer-tools --> +<!-- topics: encoding-security --> <!-- Generated from commit: 2ef8cb4d03cd338b88ee72f8d811d839f311c525 --> diff --git a/bbox-cropper.docs.md b/bbox-cropper.docs.md index cc06dfb3..0918146a 100644 --- a/bbox-cropper.docs.md +++ b/bbox-cropper.docs.md @@ -1,5 +1,5 @@ Draw bounding boxes on images using an interactive cropping tool powered by CropperJS. Load an image by pasting, dragging and dropping, or selecting a file, then click and drag to create a box around your region of interest. The tool automatically outputs normalized coordinates as percentages of the image dimensions in a format ready for command-line use. -<!-- topics: images-graphics, developer-tools --> +<!-- topics: images-graphics --> <!-- features: file-upload, drag-and-drop, clipboard --> <!-- Generated from commit: d117432950c0c71f304ef9c89da6c91a83883df4 --> diff --git a/bluesky-firehose.docs.md b/bluesky-firehose.docs.md index d68e959e..4c447cb3 100644 --- a/bluesky-firehose.docs.md +++ b/bluesky-firehose.docs.md @@ -1,5 +1,5 @@ Monitor real-time Bluesky feed data by connecting to the Bluesky Jetstream WebSocket service and viewing incoming posts and events. Send custom JSON messages to filter the feed by collection type, specific user DIDs, or other parameters, with all activity logged in the output panel for debugging and inspection. Use the provided keyboard shortcut (Ctrl/Cmd + Enter) to quickly send configuration updates to the WebSocket connection. -<!-- topics: social-feeds, developer-tools --> +<!-- topics: social-feeds --> <!-- features: websockets --> <!-- Generated from commit: 7c6af8eeabc7682b5f9ec2621e34bc771c5471d8 --> diff --git a/bluesky-resolve.docs.md b/bluesky-resolve.docs.md index eefa2130..f672599f 100644 --- a/bluesky-resolve.docs.md +++ b/bluesky-resolve.docs.md @@ -1,5 +1,5 @@ View and resolve Bluesky handles to their corresponding Decentralized Identifiers (DIDs) using the AT Protocol API. Enter a Bluesky handle in the format `username.bsky.social` to retrieve the associated DID, which serves as a unique identifier for accounts on the Bluesky network. This tool provides a simple interface for looking up handle-to-DID mappings through Bluesky's public resolver endpoint. -<!-- topics: social-feeds, developer-tools --> +<!-- topics: social-feeds --> <!-- features: fetch-network --> <!-- Generated from commit: 1472c5df0a4a8e97ee67543600403e642d504f0b --> diff --git a/box-shadow.docs.md b/box-shadow.docs.md index 74ea2fd9..f8acc4a8 100644 --- a/box-shadow.docs.md +++ b/box-shadow.docs.md @@ -1,5 +1,5 @@ Generate custom CSS box-shadow effects with interactive controls and real-time preview. Adjust horizontal and vertical offsets, blur radius, spread radius, color, and opacity using intuitive sliders and color picker to visualize shadow changes instantly. Copy the generated CSS code directly to your clipboard for immediate use in your stylesheets. -<!-- topics: css-layout, developer-tools --> +<!-- topics: css-layout --> <!-- features: clipboard --> <!-- Generated from commit: 44e0b09ad71ab22503ccf7edc0dbbec209bb2e05 --> diff --git a/broadcast-channel-chat.docs.md b/broadcast-channel-chat.docs.md index d710e21b..b0e55012 100644 --- a/broadcast-channel-chat.docs.md +++ b/broadcast-channel-chat.docs.md @@ -1,4 +1,4 @@ Send chat messages that synchronize instantly across multiple browser tabs using the Broadcast Channel API. Each tab displays messages sent from other tabs with a sync indicator, allowing real-time communication without requiring a backend server. Open multiple tabs of this page to see messages propagate automatically across all instances. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education --> <!-- Generated from commit: 569bb9004a556ab797b3f6ba7ebe14f21b7514f6 --> diff --git a/bugzilla-bug.docs.md b/bugzilla-bug.docs.md index 76b6a3fd..4df0b5db 100644 --- a/bugzilla-bug.docs.md +++ b/bugzilla-bug.docs.md @@ -1,5 +1,5 @@ View Mozilla Bugzilla bug reports with a streamlined interface that displays bug details, comments, and change history in an organized timeline format. Enter a bug ID, URL, or Bugzilla link to retrieve comprehensive information including status, dependencies, keywords, and all activity related to the bug. The viewer automatically fetches and displays details about related bugs referenced in dependencies and history changes, making it easy to navigate connections between issues. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, url-state --> <!-- Generated from commit: 96d20a53f6df95e709fc2702450febf6619c99b2 --> diff --git a/build_index.py b/build_index.py index 30c306fa..c4d59fee 100755 --- a/build_index.py +++ b/build_index.py @@ -367,6 +367,20 @@ def build_index() -> None: padding-bottom: 2px; margin: 1.4em 0 0.8em; }} + .dir-nav {{ + font-size: 0.9em; + margin: 0 0 1.4em; + line-height: 1.8; + }} + .dir-toplevel {{ + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.1em; + color: #fff; + background: linear-gradient(to bottom, rgb(154, 103, 175) 0%, rgb(100, 67, 130) 100%); + padding: 4px 10px; + margin: 1.5em 0 0.9em; + border-radius: 2px; + }} .dir-chips {{ display: flex; flex-wrap: wrap; diff --git a/chrome-prompt-playground.docs.md b/chrome-prompt-playground.docs.md index c4a2c276..ce131be5 100644 --- a/chrome-prompt-playground.docs.md +++ b/chrome-prompt-playground.docs.md @@ -1,5 +1,5 @@ Interact with Chrome's built-in language model API through this web-based playground interface. The application allows users to check model availability, download the model if needed, and execute text prompts to generate responses directly in the browser. A persistent history feature maintains records of previous prompts and responses for easy reference. -<!-- topics: ai-llm, developer-tools --> +<!-- topics: ai-llm --> <!-- features: local-storage --> <!-- Generated from commit: 1ba6752f5d7d8a2e4146993231bfef4a92945f0c --> diff --git a/claude-code-timeline.docs.md b/claude-code-timeline.docs.md index 2e200eb2..48610a8b 100644 --- a/claude-code-timeline.docs.md +++ b/claude-code-timeline.docs.md @@ -1,5 +1,5 @@ View Claude Code session `.jsonl` files as an interactive timeline with customizable filtering and search capabilities. This tool displays events chronologically, extracting conversation messages, tool calls, and file snapshots with formatted previews of text content, code blocks, and embedded images. Use the file picker, drag-and-drop, paste input, or URL fetch to load your session data and explore it with timezone switching, content-type filters, and easy JSON export. -<!-- topics: developer-tools, ai-llm --> +<!-- topics: ai-llm --> <!-- features: file-upload, drag-and-drop, fetch-network, clipboard, url-state --> <!-- Generated from commit: fdf7dab46adb9661766455cbf81a611969c6a778 --> diff --git a/claude-token-counter.docs.md b/claude-token-counter.docs.md index 7e948c57..3b9482c9 100644 --- a/claude-token-counter.docs.md +++ b/claude-token-counter.docs.md @@ -1,5 +1,5 @@ Count tokens in text and images across multiple Claude models using Anthropic's token counting API. This tool allows you to compare token usage between different Claude models, helping you optimize costs and understand how system prompts and attachments affect token counts. Simply enter your content, select which models to compare, and the tool will display token counts alongside multipliers showing relative usage. -<!-- topics: ai-llm, developer-tools --> +<!-- topics: ai-llm --> <!-- features: fetch-network, file-upload, drag-and-drop --> <!-- Generated from commit: 8533243d54be5b335d00075e3c7ff9f5c0bbcfe3 --> diff --git a/clipboard-backup.docs.md b/clipboard-backup.docs.md index 235da905..0e4eb43d 100644 --- a/clipboard-backup.docs.md +++ b/clipboard-backup.docs.md @@ -1,5 +1,5 @@ Save and manage clipboard content across multiple formats including text, HTML, RTF, and images with this clipboard backup tool. Paste any content from your clipboard to automatically create a backup that can be restored later or downloaded in its original format. All backups are stored locally in your browser using IndexedDB, giving you persistent access to your clipboard history without any external uploads or server storage. -<!-- topics: productivity, developer-tools --> +<!-- topics: productivity --> <!-- features: clipboard, indexeddb, canvas, file-upload --> <!-- Generated from commit: 75818b81671d52258cbd268a7c3b34a8685b2726 --> diff --git a/codex-timeline.docs.md b/codex-timeline.docs.md index fa2ee4f5..91b56563 100644 --- a/codex-timeline.docs.md +++ b/codex-timeline.docs.md @@ -1,5 +1,5 @@ View Mozilla Codex rollout timeline events from `.jsonl` files with an interactive interface that supports filtering, searching, and detailed event inspection. Load files via drag-and-drop, paste, or URL fetch, then explore events organized chronologically with customizable timezone display and comprehensive event details including formatted content, tool calls, and reasoning blocks. -<!-- topics: developer-tools, ai-llm --> +<!-- topics: ai-llm --> <!-- features: fetch-network, file-upload, drag-and-drop, clipboard, url-state --> <!-- Generated from commit: 266b40cbefe398ec5a03b695f107cab7a5713529 --> diff --git a/cors-fetch.docs.md b/cors-fetch.docs.md index a278fbd7..fdc1e9c8 100644 --- a/cors-fetch.docs.md +++ b/cors-fetch.docs.md @@ -1,5 +1,5 @@ Test HTTP requests directly from your browser and observe which response headers and body content are accessible under CORS (Cross-Origin Resource Sharing) restrictions. This tool lets you construct requests with custom methods, headers, and body content, import requests from curl commands, and format JSON responses for easier inspection. The application preserves your request configuration in the URL fragment, allowing you to share and bookmark specific test cases. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, url-state, clipboard --> <!-- Generated from commit: c32bcd73b70db5db6ef2fba5deba2b2d6e9807cb --> diff --git a/csp-allow.docs.md b/csp-allow.docs.md index 22db5a2c..85221089 100644 --- a/csp-allow.docs.md +++ b/csp-allow.docs.md @@ -1,5 +1,5 @@ Experiment with Content Security Policy (CSP) allow-lists by editing HTML code in the left panel and observing how network requests are handled in the sandboxed preview on the right. Add trusted origins to the connect-src allow-list, and the application will prompt you to approve blocked requests from the sandbox, automatically updating your CSP configuration. This tool helps developers understand how CSP policies control resource loading and test dynamic allow-list management in real-time. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education --> <!-- features: local-storage --> <!-- Generated from commit: 4dbfb23264757d118ca890c1d9f561ce4516ed4b --> diff --git a/curly-emdash.docs.md b/curly-emdash.docs.md index 5b8a0aa5..05d10825 100644 --- a/curly-emdash.docs.md +++ b/curly-emdash.docs.md @@ -1,4 +1,4 @@ Identify curly quotes, curly apostrophes, and em dashes in your text with this highlighting tool. Paste or type content into the input panel to see matching characters highlighted in the preview, with real-time counts for each character type. This utility helps detect typographic characters that may have been introduced through word processors or web copy. -<!-- topics: text-writing, developer-tools --> +<!-- topics: text-writing --> <!-- Generated from commit: 473a7e15e6c142be9ab4265dc39d5129ffab9ef8 --> diff --git a/deep-research-viewer.docs.md b/deep-research-viewer.docs.md index 171f943b..46e66310 100644 --- a/deep-research-viewer.docs.md +++ b/deep-research-viewer.docs.md @@ -2,6 +2,6 @@ Analyze and visualize AI deep research transcripts with this interactive viewer that displays the complete research workflow including reasoning steps, web searches, visited pages, and code executions. Load transcripts from GitHub Gists, paste JSON directly, or view example data to explore how the AI model conducted research and arrived at its final conclusions. The viewer provides statistical summaries and a chronological timeline showing the model's thinking process, search queries, page visits, and computational steps in an easy-to-read format. -<!-- topics: ai-llm, developer-tools --> +<!-- topics: ai-llm --> <!-- features: fetch-network, file-upload, url-state --> <!-- Generated from commit: a8bb00cc9d4d3c07e6d700283d7296593053e9a8 --> diff --git a/directory.py b/directory.py index b179e5ae..acce6ea6 100644 --- a/directory.py +++ b/directory.py @@ -1,79 +1,129 @@ -"""Render a classic Yahoo-style directory of tools grouped by tag. +"""Render a classic Yahoo-style directory of tools. -Produces a static HTML fragment: tools grouped by topic ("what it does") and a -second grouping by browser feature. Output works with no JavaScript; the -homepage progressively enhances it with feature-filter chips. +The directory has two levels: top-level categories (e.g. "Development & APIs") +each containing subcategories (e.g. "Developer Tools", "Code Sandboxes & REPLs"), +with the tools listed under each subcategory. A second section groups tools by +the browser feature they use. The output is static HTML that works with no +JavaScript; feature chips are anchor links into the feature section. """ from __future__ import annotations import html +from collections import defaultdict from typing import Dict, List, Sequence -def _group(tools: Sequence[dict], namespace: str, vocab_group: Dict[str, str]): - """Yield ``(slug, display_name, [tools])`` for each non-empty tag, in vocab order.""" - buckets: Dict[str, List[dict]] = {slug: [] for slug in vocab_group} +def _bucket(tools: Sequence[dict], namespace: str) -> Dict[str, List[dict]]: + """Group tools by each tag in the given namespace ('topics' or 'features').""" + buckets: Dict[str, List[dict]] = defaultdict(list) for tool in tools: for tag in tool.get(namespace, []): - buckets.setdefault(tag, []).append(tool) - - ordered = list(vocab_group) + [slug for slug in buckets if slug not in vocab_group] - for slug in ordered: - members = buckets.get(slug) - if not members: - continue - display = vocab_group.get(slug, slug.replace("-", " ").title()) - members = sorted(members, key=lambda t: t.get("title", "").lower()) - yield slug, display, members - - -def _render_section(title: str, anchor_prefix: str, groups) -> str: - blocks = [] - for slug, display, members in groups: - anchor = f"{anchor_prefix}-{slug}" - links = "\n".join( - f' <li><a href="{html.escape(tool.get("url", "#"))}">' - f'{html.escape(tool.get("title", tool.get("slug", "")))}</a></li>' - for tool in members - ) - blocks.append( - f""" <div class="dir-cat" id="{html.escape(anchor)}"> + buckets[tag].append(tool) + return buckets + + +def _display(vocab_group: Dict[str, str], slug: str) -> str: + return vocab_group.get(slug, slug.replace("-", " ").title()) + + +def _subcat_block(anchor: str, display: str, members: Sequence[dict]) -> str: + members = sorted(members, key=lambda t: t.get("title", "").lower()) + links = "\n".join( + f' <li><a href="{html.escape(tool.get("url", "#"))}">' + f'{html.escape(tool.get("title", tool.get("slug", "")))}</a></li>' + for tool in members + ) + return f""" <div class="dir-cat" id="{html.escape(anchor)}"> <h3>{html.escape(display)} <span class="dir-count">({len(members)})</span></h3> <ul> {links} </ul> </div>""" + + +def _grid(blocks: Sequence[str]) -> str: + return '<div class="dir-grid">\n' + "\n".join(blocks) + "\n</div>" + + +def _render_topics(tools: Sequence[dict], vocab: dict) -> str: + buckets = _bucket(tools, "topics") + topics_map = vocab.get("topics", {}) + categories = list(vocab.get("categories", [])) + + placed = set() + sections = [] + nav_links = [] + + def emit_category(cat_slug, cat_name, sub_slugs): + blocks = [] + for sub in sub_slugs: + members = buckets.get(sub) + if not members: + continue + blocks.append( + _subcat_block(f"topic-{sub}", _display(topics_map, sub), members) + ) + if not blocks: + return + nav_links.append( + f'<a href="#cat-{html.escape(cat_slug)}">{html.escape(cat_name)}</a>' + ) + sections.append( + f'<h3 class="dir-toplevel" id="cat-{html.escape(cat_slug)}">' + f"{html.escape(cat_name)}</h3>\n" + _grid(blocks) ) + + for cat in categories: + sub_slugs = cat.get("subcategories", []) + placed.update(sub_slugs) + emit_category(cat.get("slug", ""), cat.get("name", ""), sub_slugs) + + # Any topic tag not assigned to a category (e.g. newly coined) lands here. + leftover = [slug for slug in buckets if slug not in placed] + if leftover: + emit_category("more", "More", sorted(leftover)) + + nav = ( + '<div class="dir-nav">' + " · ".join(nav_links) + "</div>" + if nav_links + else "" + ) return ( - f'<h2 class="dir-heading">{html.escape(title)}</h2>\n' - f'<div class="dir-grid">\n' + "\n".join(blocks) + "\n</div>" + '<h2 class="dir-heading">Browse by category</h2>\n' + + nav + + "\n" + + "\n".join(sections) ) -def render_directory(tools: Sequence[dict], vocab: dict) -> str: - """Render the full directory HTML fragment from tools and the tag vocabulary.""" - topic_groups = list(_group(tools, "topics", vocab.get("topics", {}))) - feature_groups = list(_group(tools, "features", vocab.get("features", {}))) - - feature_chips = "\n".join( - f' <a class="dir-chip" href="#feature-{html.escape(slug)}" ' - f'data-feature="{html.escape(slug)}">{html.escape(display)} ' - f'<span class="dir-count">({len(members)})</span></a>' - for slug, display, members in feature_groups - ) +def _render_features(tools: Sequence[dict], vocab: dict) -> str: + buckets = _bucket(tools, "features") + features_map = vocab.get("features", {}) + ordered = [slug for slug in features_map if buckets.get(slug)] + ordered += [slug for slug in buckets if slug not in features_map] - topics_html = _render_section("Browse by category", "topic", topic_groups) - features_html = _render_section( - "Browse by browser feature", "feature", feature_groups + chips = "\n".join( + f' <a class="dir-chip" href="#feature-{html.escape(slug)}">' + f'{html.escape(_display(features_map, slug))} ' + f'<span class="dir-count">({len(buckets[slug])})</span></a>' + for slug in ordered + ) + blocks = [ + _subcat_block(f"feature-{slug}", _display(features_map, slug), buckets[slug]) + for slug in ordered + ] + return ( + '<h2 class="dir-heading">Browse by browser feature</h2>\n' + f'<div class="dir-chips">\n{chips}\n</div>\n' + _grid(blocks) ) + +def render_directory(tools: Sequence[dict], vocab: dict) -> str: + """Render the full directory HTML fragment from tools and the tag vocabulary.""" return f"""<div class="directory" data-directory> <p class="dir-intro">A classic directory of every tool, sorted into categories. -Pick a category below, or filter by the browser features a tool uses.</p> -<div class="dir-chips" data-feature-chips> -{feature_chips} -</div> -{topics_html} -{features_html} +Pick a category below, or jump to the browser features a tool uses.</p> +{_render_topics(tools, vocab)} +{_render_features(tools, vocab)} </div>""" diff --git a/dns.docs.md b/dns.docs.md index a577dbc5..b879e80f 100644 --- a/dns.docs.md +++ b/dns.docs.md @@ -2,6 +2,6 @@ Query DNS records for any domain using Cloudflare's DNS-over-HTTPS API with support for multiple record types (A, AAAA, CNAME, MX, NS, TXT, SOA, CAA, SRV, PTR) and three different resolvers. Choose between the standard 1.1.1.1 resolver, the malware-blocking 1.1.1.2, or the family-friendly 1.1.1.3 that filters both malware and adult content. Results display in an easy-to-read table format with TTL values, response flags, and status information, with an option to view raw JSON responses or query all record types at once. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, clipboard, url-state --> <!-- Generated from commit: d473b6be87fd089c1c5fc81d40e12f68141a405b --> diff --git a/dot.docs.md b/dot.docs.md index f9e78f07..209e9ece 100644 --- a/dot.docs.md +++ b/dot.docs.md @@ -1,5 +1,5 @@ Render DOT graph files into visual diagrams directly in your browser. Paste your DOT syntax into the textarea and the graph will automatically render as an SVG visualization, with live updates as you edit. Share your graphs by copying the URL, which encodes your DOT content in the fragment identifier. -<!-- topics: developer-tools, data-visualization --> +<!-- topics: data-visualization --> <!-- features: svg, url-state, webassembly --> <!-- Generated from commit: a3fec50f7e8b7b0276fa19aca3f3bb61fb60130d --> diff --git a/emoji-identifier.docs.md b/emoji-identifier.docs.md index d4a375b2..ae833646 100644 --- a/emoji-identifier.docs.md +++ b/emoji-identifier.docs.md @@ -1,5 +1,5 @@ Extract and identify all emojis from text by pasting or typing into the input field, and instantly view their names and Unicode codepoint values. The tool uses a comprehensive emoji detection regex pattern combined with a Unicode emoji dataset to recognize a wide variety of emoji characters, including skin tone variants and zero-width joiner sequences. Results are displayed in real-time, showing each unique emoji found along with its standardized name and corresponding Unicode representation. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education --> <!-- features: fetch-network --> <!-- Generated from commit: 5072713dbebf789683182021f37c6b3f654008a4 --> diff --git a/escape-entities.docs.md b/escape-entities.docs.md index a6f0af24..b69dfda8 100644 --- a/escape-entities.docs.md +++ b/escape-entities.docs.md @@ -1,5 +1,5 @@ Convert between special characters and their HTML entity representations with this bidirectional encoding tool. Select between Escape mode to convert characters like `<`, `>`, `&`, and quotes into their corresponding HTML entities, or Unescape mode to decode HTML entities back into readable characters. The tool supports named entities, decimal numeric references, and hexadecimal numeric references, with real-time conversion displayed in the output field. -<!-- topics: developer-tools, encoding-security --> +<!-- topics: encoding-security --> <!-- features: clipboard --> <!-- Generated from commit: d8fd1ad5e6048ea6e1f8df91fe531f13cbc6dd3f --> diff --git a/exif.docs.md b/exif.docs.md index 77397342..3a019585 100644 --- a/exif.docs.md +++ b/exif.docs.md @@ -1,5 +1,5 @@ Extract EXIF metadata and GPS coordinates from uploaded images using this viewer. Simply upload or drag-and-drop an image file to instantly display all embedded EXIF data, including GPS latitude and longitude if available. The tool supports common image formats such as JPEG, PNG, and HEIC. -<!-- topics: images-graphics, developer-tools --> +<!-- topics: images-graphics --> <!-- features: file-upload, drag-and-drop --> <!-- Generated from commit: 646e64b51e917dc72a0f8d86232b016e785722aa --> diff --git a/extract-urls.docs.md b/extract-urls.docs.md index 38b36320..bf551552 100644 --- a/extract-urls.docs.md +++ b/extract-urls.docs.md @@ -1,5 +1,5 @@ Extract URLs from copied web page content by pasting HTML into the input area, which automatically identifies and displays all hyperlinks found in the pasted material. The tool filters for valid HTTP links and provides a consolidated list in the output textarea, making it easy to copy all extracted URLs to your clipboard with a single button click. -<!-- topics: developer-tools, text-writing --> +<!-- topics: text-writing --> <!-- features: clipboard --> <!-- Generated from commit: 0f7fb49fd53d83ca1648b4db931c69acf9605529 --> diff --git a/ffmpeg-crop.docs.md b/ffmpeg-crop.docs.md index 344f620a..c12fc40c 100644 --- a/ffmpeg-crop.docs.md +++ b/ffmpeg-crop.docs.md @@ -1,5 +1,5 @@ Generate FFmpeg crop commands by uploading a video file and interactively defining a crop area using a draggable overlay. The tool provides both standard and iPhone-compatible FFmpeg command formats that automatically update as you adjust the crop box dimensions and position. This eliminates the need to manually calculate crop parameters for video editing workflows. -<!-- topics: audio-video, developer-tools --> +<!-- topics: audio-video --> <!-- features: file-upload --> <!-- Generated from commit: c86f2226030d4506d32d7d652231d0cd60f0c17b --> diff --git a/gif-dissector.docs.md b/gif-dissector.docs.md index b04fc0f6..1fc062cc 100644 --- a/gif-dissector.docs.md +++ b/gif-dissector.docs.md @@ -1,5 +1,5 @@ Parse and visualize animated GIF files by extracting individual frames, timing data, color palettes, and detailed metadata. Upload a GIF file to instantly decompose it into its constituent frames with precise delay measurements, disposal methods, transparency information, and global color table analysis. The tool renders composited frames to show exactly how the animation appears, while providing comprehensive technical details about the image structure and properties. -<!-- topics: images-graphics, developer-tools --> +<!-- topics: images-graphics --> <!-- features: canvas, file-upload, drag-and-drop --> <!-- Generated from commit: 8d36bfd6bedeb8fae0e829b140f4fef04216e0b6 --> diff --git a/github-account.docs.md b/github-account.docs.md index fa04695d..bb078834 100644 --- a/github-account.docs.md +++ b/github-account.docs.md @@ -1,5 +1,5 @@ Look up GitHub user profiles and account information by username or numeric account ID. This tool fetches account details from the GitHub REST API, displaying information such as the user's name, login handle, account ID, creation date, and profile avatar. The application stores rate limit information locally to prevent repeated requests during API throttling periods. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, local-storage, url-state --> <!-- Generated from commit: 8fe6f1d70bd695e2f8e1cc9458e0c77a39c470a9 --> diff --git a/github-api-write.docs.md b/github-api-write.docs.md index 2a2c9345..16670f47 100644 --- a/github-api-write.docs.md +++ b/github-api-write.docs.md @@ -1,5 +1,5 @@ Upload files and images to GitHub repositories using the GitHub API. This tool accepts either text content or image files and commits them to a specified repository path with proper authentication via personal access tokens. The interface automatically adapts to show relevant input fields based on whether you're uploading text or an image file. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, file-upload --> <!-- Generated from commit: 4b7902dd659f4a47a4f3e751198fa8b48b5c3514 --> diff --git a/github-graphiql.docs.md b/github-graphiql.docs.md index 1944b4b7..ca4606c7 100644 --- a/github-graphiql.docs.md +++ b/github-graphiql.docs.md @@ -1,5 +1,5 @@ Explore GitHub's GraphQL API using an interactive query interface that requires authentication via a personal access token. Enter your GitHub token to connect and start writing, executing, and testing GraphQL queries against GitHub's data in real-time. The explorer provides syntax highlighting, query validation, and response inspection capabilities within an embedded GraphiQL environment. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, local-storage --> <!-- Generated from commit: a877d8ffb396e42868a1a429b302b674fe100970 --> diff --git a/github-issue-to-markdown.docs.md b/github-issue-to-markdown.docs.md index 388dee81..dc181bc6 100644 --- a/github-issue-to-markdown.docs.md +++ b/github-issue-to-markdown.docs.md @@ -2,6 +2,6 @@ Convert GitHub issues and pull requests to markdown format by providing their URL and an optional personal access token for private repositories. The tool automatically fetches the issue details, all comments, and expands any inline code references with their actual content from the repository. Your GitHub token is securely stored in your browser's local storage for convenient access on subsequent visits. -<!-- topics: developer-tools, text-writing --> +<!-- topics: text-writing, apis-services --> <!-- features: fetch-network, local-storage, clipboard --> <!-- Generated from commit: 2a0a0c26db427db87f0aa937c96a7da01b8f8994 --> diff --git a/github-ratelimit.docs.md b/github-ratelimit.docs.md index 5c660147..aa10cf71 100644 --- a/github-ratelimit.docs.md +++ b/github-ratelimit.docs.md @@ -1,5 +1,5 @@ Monitor your GitHub API usage and remaining rate limits with this authentication-based checker. After authenticating with your GitHub account, the tool displays detailed information about your API quotas across different resource types, including remaining calls, reset times, and visual progress indicators. The interface shows critical warnings when your limits are running low, helping you manage your API consumption effectively. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, local-storage --> <!-- Generated from commit: d6b0634ce65c95cd5d55061c1cfcb03778b33419 --> diff --git a/github-repo-size.docs.md b/github-repo-size.docs.md index cda2acad..0f136711 100644 --- a/github-repo-size.docs.md +++ b/github-repo-size.docs.md @@ -1,5 +1,5 @@ Check the size of any GitHub repository by entering the owner and repository name or pasting a GitHub URL. The tool fetches repository data from the GitHub API and displays the total size in kilobytes, megabytes, or gigabytes depending on the repository's scale. Results are automatically saved to the browser URL, allowing you to share or revisit repository size checks. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, url-state --> <!-- Generated from commit: 24e094de34a2936a429e6fce8f6c736039c1d9c7 --> diff --git a/github-repo-stats.docs.md b/github-repo-stats.docs.md index bb8063f0..ff799856 100644 --- a/github-repo-stats.docs.md +++ b/github-repo-stats.docs.md @@ -1,5 +1,5 @@ View GitHub repository statistics including commit counts, contributor information, language breakdowns, and release details by entering a repository name or URL. This tool fetches data directly from the GitHub REST API in your browser, displaying comprehensive metrics such as stars, forks, branches, tags, and activity timestamps. Optionally authenticate with GitHub to increase your API rate limit from 60 to 5,000 requests per hour. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, local-storage, url-state --> <!-- Generated from commit: 8d4ba6e137643813d6112e820cf2cbfe75317b90 --> diff --git a/html-preview.docs.md b/html-preview.docs.md index 959d720d..e2c6c769 100644 --- a/html-preview.docs.md +++ b/html-preview.docs.md @@ -1,5 +1,5 @@ Write HTML code directly in the editor pane and see the rendered output update in real-time in the preview pane. The editor supports live preview with debounced updates to prevent excessive rendering, and includes a copy button to save your HTML code to the clipboard. On mobile devices, toggle between the editor and preview views using the dedicated button in the toolbar. -<!-- topics: developer-tools --> +<!-- topics: code-sandboxes --> <!-- features: clipboard --> <!-- Generated from commit: a418a01e7b7aeae97b6992d21d1f93c04bacd8b8 --> diff --git a/huggingface-storage.docs.md b/huggingface-storage.docs.md index d84d704c..da86bec6 100644 --- a/huggingface-storage.docs.md +++ b/huggingface-storage.docs.md @@ -1,5 +1,5 @@ Check the storage size of Hugging Face machine learning models by entering a model URL or repository path. The tool queries the Hugging Face API to retrieve the total storage used by the specified model and displays the result in a human-readable format (MB or GB). Models can be looked up using either their full Hugging Face URL or their model identifier in the format `username/model-name`. -<!-- topics: ai-llm, developer-tools --> +<!-- topics: ai-llm, apis-services --> <!-- features: fetch-network --> <!-- Generated from commit: ab388dda297c98a8de2e111486fa2450f96fdf84 --> diff --git a/iframe-resize.docs.md b/iframe-resize.docs.md index 9cedc55a..2fe94361 100644 --- a/iframe-resize.docs.md +++ b/iframe-resize.docs.md @@ -1,4 +1,4 @@ Embed untrusted content safely within a webpage using a sandboxed iframe that automatically adjusts its height without allowing cross-origin access. The prototype uses `postMessage` to communicate height changes between the sandboxed iframe and parent page, enabling seamless content display while maintaining security restrictions. Various content examples demonstrate how the sandbox handles dynamic content, images, and attempts at malicious behavior. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education --> <!-- Generated from commit: 6e88344d337ee402c4fe06390fe5f8ce69be81ed --> diff --git a/iframe-sandbox.docs.md b/iframe-sandbox.docs.md index bae09ccf..9a46e378 100644 --- a/iframe-sandbox.docs.md +++ b/iframe-sandbox.docs.md @@ -1,4 +1,4 @@ Test and explore HTML, CSS, and JavaScript code in a sandboxed iframe environment with configurable security restrictions. The left panel provides a code editor for writing HTML content, while the right panel displays a live preview with customizable sandbox attributes that control what the iframe can access and execute. Use the checkboxes to enable or disable specific permissions like scripts, forms, popups, and same-origin access to understand how sandbox restrictions affect web content behavior. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education, code-sandboxes --> <!-- Generated from commit: e62bd12ff34fdeb7a906f9b34303c17ea63d3a41 --> diff --git a/incomplete-json-printer.docs.md b/incomplete-json-printer.docs.md index 8124faaf..c344bb0f 100644 --- a/incomplete-json-printer.docs.md +++ b/incomplete-json-printer.docs.md @@ -1,5 +1,5 @@ Format truncated or incomplete JSON into readable structures with automatic live formatting as you type. This tool applies consistent indentation and proper spacing to malformed or partial JSON snippets, and displays validation status while the formatted output can be copied to the clipboard. Example data is available to test the functionality. -<!-- topics: data-json, developer-tools --> +<!-- topics: data-json --> <!-- features: clipboard --> <!-- Generated from commit: 390a83ad24b691c897b16de5565fecbf9c63c8cc --> diff --git a/jina-reader.docs.md b/jina-reader.docs.md index 8ca3c068..6d13e935 100644 --- a/jina-reader.docs.md +++ b/jina-reader.docs.md @@ -1,5 +1,5 @@ Convert web pages to structured content using the Jina Reader API, with support for multiple output formats including markdown, HTML, and text. The interface allows you to fetch and preview page content while optionally running AI-powered analysis through Claude to generate summaries, extract quotes, and identify key ideas from the retrieved material. -<!-- topics: ai-llm, developer-tools --> +<!-- topics: ai-llm, apis-services --> <!-- features: fetch-network, local-storage, clipboard --> <!-- Generated from commit: 0e83c1a01b476b112d05f3d57972c31907b21bdc --> diff --git a/json-diff.docs.md b/json-diff.docs.md index d327f991..b42952a7 100644 --- a/json-diff.docs.md +++ b/json-diff.docs.md @@ -1,4 +1,4 @@ Compare JSON documents side-by-side to identify additions, removals, and modifications between two versions. The tool displays differences with color-coded highlighting and provides character-level detail for string changes, making it easy to spot exactly what has changed. Preloaded examples are available to explore common use cases like configuration updates, user profile changes, and API response comparisons. -<!-- topics: data-json, developer-tools --> +<!-- topics: data-json --> <!-- Generated from commit: f98c630bbb2b7e1004a0a184274d88c3f9ab86df --> diff --git a/json-schema-builder.docs.md b/json-schema-builder.docs.md index fd75f044..0765d918 100644 --- a/json-schema-builder.docs.md +++ b/json-schema-builder.docs.md @@ -1,5 +1,5 @@ Create JSON schemas interactively with this builder tool that allows you to define properties, set data types, and configure nested objects through an intuitive form interface. The generated schema is displayed in real-time and can be copied to your clipboard for use in your applications. Your schema is automatically saved in the URL, making it easy to share or revisit your work later. -<!-- topics: data-json, developer-tools --> +<!-- topics: data-json --> <!-- features: clipboard, url-state --> <!-- Generated from commit: 0a186e5a3a939fc9e9679ecc31068494c1368b99 --> diff --git a/json-string-extractor.docs.md b/json-string-extractor.docs.md index 361df895..a1377436 100644 --- a/json-string-extractor.docs.md +++ b/json-string-extractor.docs.md @@ -1,5 +1,5 @@ Extract all strings from JSON data that exceed 20 characters in length or contain line breaks. This tool is useful for identifying longer text content within complex JSON structures for review, localization, or documentation purposes. Simply paste JSON into the textarea to automatically display matching strings along with their object paths, and use the copy button to quickly transfer any string to your clipboard. -<!-- topics: data-json, developer-tools --> +<!-- topics: data-json --> <!-- features: clipboard, fetch-network, url-state --> <!-- Generated from commit: 6fbfc694190f24e8c08abfd816cdf64edf42f3a1 --> diff --git a/justhtml.docs.md b/justhtml.docs.md index db1e8ae5..902ca583 100644 --- a/justhtml.docs.md +++ b/justhtml.docs.md @@ -1,5 +1,5 @@ Test the JustHTML Python HTML5 parser directly in your browser with this interactive playground. Parse, query, and manipulate HTML using CSS selectors, pretty-print documents, extract text content, and convert HTML to Markdown—all running client-side with Pyodide. The playground supports multiple analysis modes including tree structure visualization and streaming event inspection for comprehensive HTML document exploration. -<!-- topics: developer-tools --> +<!-- topics: code-sandboxes --> <!-- features: webassembly, fetch-network --> <!-- Generated from commit: 172cd5ab9919eda995b8162c87b84bea7d58fb3a --> diff --git a/link-extractor.docs.md b/link-extractor.docs.md index ad56a370..488bb925 100644 --- a/link-extractor.docs.md +++ b/link-extractor.docs.md @@ -1,5 +1,5 @@ Extract hyperlinks from pasted web content and export them in multiple formats including HTML, Markdown, and plain text. The tool automatically detects and removes duplicate links while displaying each link's title and URL for easy verification. Copy extracted links in your preferred format with a single click. -<!-- topics: developer-tools, productivity --> +<!-- topics: productivity --> <!-- features: clipboard --> <!-- Generated from commit: daa72d910518f56743f4c97a6bfce23001d6c3c1 --> diff --git a/manyana.docs.md b/manyana.docs.md index 339df950..f7e0a913 100644 --- a/manyana.docs.md +++ b/manyana.docs.md @@ -2,6 +2,6 @@ Explore how generation-counting conflict resolution works in distributed systems by editing two independent document branches and observing their deterministic merge. This interactive tool demonstrates the Manyana merge algorithm, where each state entry carries a count field that determines whether content is live (odd count) or deleted (even count)—allowing re-adds to automatically win over deletions during merge. Built with Python via Pyodide, it runs entirely in your browser with live rendering of merge trees, conflict detection, and detailed state inspection. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education --> <!-- features: webassembly --> <!-- Generated from commit: 91ddc6c343064cca1482985e59603791ed1882cf --> diff --git a/mask-visualizer.docs.md b/mask-visualizer.docs.md index 90056d5f..3e2983d4 100644 --- a/mask-visualizer.docs.md +++ b/mask-visualizer.docs.md @@ -1,4 +1,4 @@ Visualize bounding boxes and PNG masks from JSON data with support for multiple coordinate system origins. This tool accepts JSON input containing box coordinates and base64-encoded mask images, then displays them overlaid on an interactive canvas with real-time coordinate transformation. The visualization includes detailed information about each item's original and transformed coordinates based on the selected origin point. -<!-- topics: images-graphics, developer-tools --> +<!-- topics: images-graphics --> <!-- Generated from commit: e0cc858feb348a0430c056612c7c9aa5171e54ae --> diff --git a/mdn-timelines.docs.md b/mdn-timelines.docs.md index 95752c63..9a7c552b 100644 --- a/mdn-timelines.docs.md +++ b/mdn-timelines.docs.md @@ -1,5 +1,5 @@ View Mozilla's browser compatibility data to track when web APIs were first supported across different browsers. Search for any API by name to see a chronological timeline of support additions, including release dates and version numbers for each browser. The interface also displays relevant MDN documentation links, specification URLs, and status indicators to help developers understand the maturity and adoption timeline of web platform features. -<!-- topics: reference-education, developer-tools --> +<!-- topics: reference-education --> <!-- features: fetch-network, url-state --> <!-- Generated from commit: 41ce0b8bbae876c4abd9549ce34f13bb37f07c16 --> diff --git a/micropython.docs.md b/micropython.docs.md index bc054d5b..2c87df5a 100644 --- a/micropython.docs.md +++ b/micropython.docs.md @@ -1,5 +1,5 @@ Execute Python code in a sandboxed MicroPython WebAssembly environment with output displayed in real-time. Code is automatically saved to the URL for convenient sharing and persistence, and the environment supports JavaScript interoperability including the `fetch()` API for making HTTP requests. Built-in examples demonstrate common programming patterns from basic operations to working with APIs. -<!-- topics: developer-tools --> +<!-- topics: code-sandboxes --> <!-- features: webassembly, url-state, fetch-network --> <!-- Generated from commit: 425e8773f146b1678787bd972744fc309317849c --> diff --git a/microquickjs.docs.md b/microquickjs.docs.md index d94deec3..c8b66cc3 100644 --- a/microquickjs.docs.md +++ b/microquickjs.docs.md @@ -1,5 +1,5 @@ Execute JavaScript code in a lightweight MicroQuickJS sandbox environment running via WebAssembly, with results displayed directly on the page. The sandbox supports ES5-like JavaScript features and automatically saves your code in the URL for easy sharing and recovery. Choose between optimized and original WebAssembly versions, try built-in examples, and use Ctrl+Enter to quickly run your code. -<!-- topics: developer-tools --> +<!-- topics: code-sandboxes --> <!-- features: webassembly, url-state --> <!-- Generated from commit: a226383c7fc2643d4087fdfe9e52c780849bb270 --> diff --git a/mp3-inspector.docs.md b/mp3-inspector.docs.md index 16737716..e9ec6686 100644 --- a/mp3-inspector.docs.md +++ b/mp3-inspector.docs.md @@ -1,5 +1,5 @@ Extract ID3 metadata and file information from MP3 audio files using this browser-based tool. Upload an MP3 file by dragging it onto the drop zone or selecting it through the file picker, and the inspector will parse and display all available tags including title, artist, album art, technical encoding details, and embedded URLs. The tool organizes metadata into categorized sections and provides a raw JSON view for advanced inspection of the complete tag data. -<!-- topics: audio-video, developer-tools --> +<!-- topics: audio-video --> <!-- features: file-upload, drag-and-drop --> <!-- Generated from commit: f0459f33e119d4e5aa757fb58b00798d8290a4c6 --> diff --git a/nav-for-headings.docs.md b/nav-for-headings.docs.md index f715f2fe..a5819827 100644 --- a/nav-for-headings.docs.md +++ b/nav-for-headings.docs.md @@ -1,4 +1,4 @@ Process HTML content to automatically generate unique IDs for all header elements and create a table of contents with anchor links. This tool is useful for adding navigation functionality to static HTML pages or preparing content for documentation systems that require header identification. Simply paste your HTML and provide the page URL, then the processor will output the modified HTML and a formatted list of clickable header links. -<!-- topics: developer-tools, text-writing --> +<!-- topics: text-writing --> <!-- Generated from commit: 2dbdc12b1eecf73a8a8b51c3b221774e149a2048 --> diff --git a/numpy-pyodide-lab.docs.md b/numpy-pyodide-lab.docs.md index c3e09f33..435e83d8 100644 --- a/numpy-pyodide-lab.docs.md +++ b/numpy-pyodide-lab.docs.md @@ -1,5 +1,5 @@ Execute NumPy vector and matrix operations directly in your browser using an interactive lab powered by Pyodide. Work through five hands-on exercises covering elementwise operations, dot products, matrix multiplication, broadcasting, and indexing, then experiment freely in the playground sandbox with instant Python output. -<!-- topics: reference-education, developer-tools --> +<!-- topics: reference-education, code-sandboxes --> <!-- features: webassembly --> <!-- Generated from commit: e862c3e3f7bc21edfb7841e6fd02c7c9a2963eca --> diff --git a/passkeys.docs.md b/passkeys.docs.md index eb8b64c0..08218c31 100644 --- a/passkeys.docs.md +++ b/passkeys.docs.md @@ -1,5 +1,5 @@ Experiment with passkey registration and authentication using the WebAuthn API in your browser. This demo allows you to create passkey credentials, authenticate with them, and inspect the underlying protocol responses and data. Stored credentials are maintained locally in your browser's storage, making this a fully client-side implementation for learning how modern passwordless authentication works. -<!-- topics: developer-tools, encoding-security --> +<!-- topics: encoding-security --> <!-- features: local-storage --> <!-- Generated from commit: 6b0d8cdc263599b8460c5d2c77b78ab57f15d11e --> diff --git a/paste-html-subset.docs.md b/paste-html-subset.docs.md index 73d1164e..1f8b9593 100644 --- a/paste-html-subset.docs.md +++ b/paste-html-subset.docs.md @@ -1,5 +1,5 @@ Convert rich text content from clipboard into clean, filtered HTML containing only semantic elements like paragraphs, headings, lists, links, and text formatting. Paste formatted content into the editable area to automatically extract and sanitize the HTML, removing unsupported tags and attributes while preserving the document structure and links. The cleaned HTML is displayed in a code editor and rendered in a live preview, with options to copy the code or clear all content. -<!-- topics: developer-tools, text-writing --> +<!-- topics: text-writing --> <!-- features: clipboard --> <!-- Generated from commit: 6f910f4c39655775c56d02ce6e4a4693d2cfdc42 --> diff --git a/paste-rich-text.docs.md b/paste-rich-text.docs.md index bd3694d2..ff3425d7 100644 --- a/paste-rich-text.docs.md +++ b/paste-rich-text.docs.md @@ -1,5 +1,5 @@ Extract HTML code from formatted text by pasting rich content into this tool, which automatically captures and displays the underlying HTML markup. The tool provides both the raw HTML code for editing and a live preview of how the formatted content renders. Use the copy button to quickly transfer the extracted HTML to your clipboard, or clear the interface to process new content. -<!-- topics: developer-tools, text-writing --> +<!-- topics: text-writing --> <!-- features: clipboard --> <!-- Generated from commit: 49c382ea7f933d489d57cc434db2314f1120886b --> diff --git a/php-deserializer.docs.md b/php-deserializer.docs.md index f2718054..6fdfb0cb 100644 --- a/php-deserializer.docs.md +++ b/php-deserializer.docs.md @@ -1,5 +1,5 @@ Convert serialized PHP data to JSON format for easy viewing and manipulation. Paste your PHP serialized string into the input field to automatically parse and display the equivalent JSON output. Use the copy button to quickly transfer the JSON to your clipboard. -<!-- topics: developer-tools, data-json --> +<!-- topics: data-json --> <!-- features: clipboard --> <!-- Generated from commit: 4c11c72c3badd4f2754287461b3c3b1a5dfc8d73 --> diff --git a/pretext-explainer.docs.md b/pretext-explainer.docs.md index 50dc9a0f..b9bd4940 100644 --- a/pretext-explainer.docs.md +++ b/pretext-explainer.docs.md @@ -1,5 +1,5 @@ Explore how pure-JavaScript text measurement and line breaking work through an interactive visualization of the Pretext library's pipeline. This tool demonstrates each stage from raw text input through whitespace normalization, word segmentation, canvas-based width measurement, and arithmetic-based line breaking, with live verification against actual DOM rendering. Drag sliders, switch fonts, and test different text samples to see how the engine handles emojis, CJK characters, Arabic text, and complex punctuation rules — all computed without touching the DOM. -<!-- topics: reference-education, developer-tools --> +<!-- topics: reference-education --> <!-- features: canvas --> <!-- Generated from commit: d8deb83eccc52c604277da785fe489f421d6f3d5 --> diff --git a/prompt-caching.docs.md b/prompt-caching.docs.md index 9586c21c..306a7d61 100644 --- a/prompt-caching.docs.md +++ b/prompt-caching.docs.md @@ -1,5 +1,5 @@ Explore OpenAI's prompt caching feature by testing different prompt structures and observing cache hit rates across multiple requests. This interactive playground lets you compose system instructions, document context, and user questions, then send them to the Chat Completions or Responses API to track how cached tokens reduce costs and improve performance. Load pre-built scenarios to compare caching behavior—such as sending identical instructions with different questions to see cache hits, or swapping documents while keeping instructions static to measure prefix reuse. -<!-- topics: ai-llm, developer-tools --> +<!-- topics: ai-llm --> <!-- features: fetch-network, local-storage --> <!-- Generated from commit: 1d6baf40110241775a4260d330a28cd23cb5cfd9 --> diff --git a/prompts-js.docs.md b/prompts-js.docs.md index 8cb57e12..57251991 100644 --- a/prompts-js.docs.md +++ b/prompts-js.docs.md @@ -1,4 +1,4 @@ Prompts.js is a lightweight JavaScript library that provides modal dialog functionality for creating alert, confirm, and prompt interactions in web applications. The library enables developers to display user-facing dialogs with async/await syntax, making it easy to handle user responses in a clean, readable manner. This demo page allows you to test the three core dialog types and view the results of user interactions. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education --> <!-- Generated from commit: 3d76b539136afa6310dfc1bdcb681f4d038f5253 --> diff --git a/pyodide-repl.docs.md b/pyodide-repl.docs.md index cad3757d..ee2d219b 100644 --- a/pyodide-repl.docs.md +++ b/pyodide-repl.docs.md @@ -1,5 +1,5 @@ Execute Python code directly in your web browser using Pyodide, a port of CPython to WebAssembly. This REPL provides an interactive Python environment with support for multiple Pyodide versions, single-line and multi-line input modes, and command history navigation. The interface is optimized for both desktop and mobile devices, with a dark theme and responsive layout that prevents content from being hidden behind on-screen keyboards. -<!-- topics: developer-tools --> +<!-- topics: code-sandboxes --> <!-- features: webassembly, url-state --> <!-- Generated from commit: 16e1d75e895b23d90e56019c13b3eb892c2cc1a9 --> diff --git a/pypi-changelog.docs.md b/pypi-changelog.docs.md index f1e0bc33..1817dca8 100644 --- a/pypi-changelog.docs.md +++ b/pypi-changelog.docs.md @@ -2,6 +2,6 @@ Track code changes across Python package versions by comparing wheel distributions from PyPI. Enter any package name to view all released versions with wheel files and generate side-by-side diffs of the changes between any two versions. The tool extracts and compares all text files from the wheels, intelligently handling binary files and package metadata renames while preserving the full context of modifications. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, clipboard, url-state --> <!-- Generated from commit: 725b699d9cd14fffee0ca6bc529cf4565017ca0c --> diff --git a/python-comment-stripper.docs.md b/python-comment-stripper.docs.md index ca668f98..adde94e6 100644 --- a/python-comment-stripper.docs.md +++ b/python-comment-stripper.docs.md @@ -1,5 +1,5 @@ Remove all comments from Python source code while preserving strings, docstrings, and code structure using the `tokenize` module running on Pyodide. Paste your Python code into the input panel, and the tool automatically strips comments in real-time, with the ability to copy the cleaned output to your clipboard. The application runs entirely in the browser without requiring a local Python installation. -<!-- topics: developer-tools, text-writing --> +<!-- topics: text-writing --> <!-- features: webassembly, clipboard --> <!-- Generated from commit: f763a6ea5887c08e0b8bc45e03b1466d14e78c02 --> diff --git a/python-vulnerability-lookup.docs.md b/python-vulnerability-lookup.docs.md index 6dde4cee..74926efd 100644 --- a/python-vulnerability-lookup.docs.md +++ b/python-vulnerability-lookup.docs.md @@ -1,5 +1,5 @@ Search Python packages for known security vulnerabilities by pasting a `pyproject.toml` or `requirements.txt` file, or by loading dependencies directly from a GitHub repository. The tool queries the OSV.dev vulnerability database and displays detailed information about any identified vulnerabilities, including severity levels, affected version ranges, and links to full disclosure reports. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, clipboard, url-state --> <!-- Generated from commit: d9bada923955fcb60708b9271a303b2722a44e5c --> diff --git a/quickjs.docs.md b/quickjs.docs.md index 3d46c2ff..c7a3424e 100644 --- a/quickjs.docs.md +++ b/quickjs.docs.md @@ -1,5 +1,5 @@ Execute JavaScript code in a sandboxed QuickJS WebAssembly environment with a built-in synchronous `fetch()` function for retrieving remote content. Code is automatically encoded in the URL hash, allowing you to easily share executable snippets with others. The interface provides a collection of ready-to-run examples covering common programming tasks and JavaScript features, making it useful for learning, testing, and demonstrating code behavior. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education, code-sandboxes --> <!-- features: webassembly, url-state, clipboard, fetch-network --> <!-- Generated from commit: a226383c7fc2643d4087fdfe9e52c780849bb270 --> diff --git a/redis-array.docs.md b/redis-array.docs.md index e5820bb0..ba9b8bee 100644 --- a/redis-array.docs.md +++ b/redis-array.docs.md @@ -2,6 +2,6 @@ Explore Redis array commands in an interactive web-based environment compiled to WebAssembly. This playground lets you execute AR* commands against an in-memory Redis instance, visualize keyspace contents, and inspect command documentation with live syntax previews. The implementation uses the sparse array data structure from the antirez:array branch, exposing commands like ARSET, ARGET, ARGREP, and others alongside a console that displays all executed commands and their responses. -<!-- topics: developer-tools, sqlite-databases --> +<!-- topics: sqlite-databases --> <!-- features: webassembly, local-storage --> <!-- Generated from commit: 69d05ef2c5e267f0600e379bc758e22d8d544e58 --> diff --git a/render-claude-citations.docs.md b/render-claude-citations.docs.md index d9a641f9..d92a2771 100644 --- a/render-claude-citations.docs.md +++ b/render-claude-citations.docs.md @@ -1,4 +1,4 @@ Render Claude API responses with proper citation formatting by pasting JSON output into this tool. The tool parses the response structure and displays text content alongside blockquote-formatted citations, making it easy to review how Claude has sourced and attributed information. An embedded iframe renderer safely displays the formatted output with styling that highlights cited passages. -<!-- topics: ai-llm, developer-tools --> +<!-- topics: ai-llm --> <!-- Generated from commit: d97ff4e32f32e064c3fa0c26f1efba6d32655355 --> diff --git a/render-markdown.docs.md b/render-markdown.docs.md index 3cf541d5..953ca466 100644 --- a/render-markdown.docs.md +++ b/render-markdown.docs.md @@ -1,5 +1,5 @@ Convert markdown text to HTML using GitHub's markdown rendering API. The tool provides a live preview of the rendered output and allows you to copy the generated HTML or rich text to your clipboard. Additional options include GitHub Flavored Markdown support and automatic cleanup of hidden HTML elements and metadata. -<!-- topics: text-writing, developer-tools --> +<!-- topics: text-writing --> <!-- features: fetch-network, clipboard --> <!-- Generated from commit: 91bfd29ff0279ad7e7666b1f6047ab571007990c --> diff --git a/rtf-to-html.docs.md b/rtf-to-html.docs.md index e78237b2..ee405a28 100644 --- a/rtf-to-html.docs.md +++ b/rtf-to-html.docs.md @@ -1,5 +1,5 @@ Convert Rich Text Format (RTF) documents to HTML with preserved formatting, colors, and styling. Paste RTF content from your clipboard to automatically extract the color table and convert text formatting including bold styling, text colors, and background colors into inline HTML styles. The converter displays the raw RTF data, generated HTML code, and a live preview of the formatted output all in one interface. -<!-- topics: text-writing, developer-tools --> +<!-- topics: text-writing --> <!-- features: clipboard --> <!-- Generated from commit: 20db4718bdf4d2f5bc8c354f345fdde34cfc650e --> diff --git a/schema-dsl.docs.md b/schema-dsl.docs.md index 610aa0fc..77680473 100644 --- a/schema-dsl.docs.md +++ b/schema-dsl.docs.md @@ -1,4 +1,4 @@ Convert a compact schema definition language into JSON schema format in real-time. This tool accepts a concise DSL where you specify field names, types (str, int, float, bool), and optional descriptions, then automatically generates the corresponding JSON schema. The converter supports both object schemas and array item schemas through the "Array items schema" option. -<!-- topics: developer-tools, data-json --> +<!-- topics: data-json --> <!-- Generated from commit: e3f47637ebdf7e83155643cae1c0def78c7caf93 --> diff --git a/software-heritage-repo.docs.md b/software-heritage-repo.docs.md index 31d4c53b..345453ea 100644 --- a/software-heritage-repo.docs.md +++ b/software-heritage-repo.docs.md @@ -1,5 +1,5 @@ Download archived Git repositories from Software Heritage, the universal archive of software source code. This tool queries the Software Heritage GraphQL API to locate repositories and creates downloadable bare Git archives through the vault service. Enter a repository URL to retrieve the latest snapshot and access detailed archive information including the Software Heritage identifier (SWHID) for future reference. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: fetch-network, url-state --> <!-- Generated from commit: dc4748ca4471e30f9fd8b108c99d918fb5f65a43 --> diff --git a/sql-pretty-printer.docs.md b/sql-pretty-printer.docs.md index c2460b87..bbacb98e 100644 --- a/sql-pretty-printer.docs.md +++ b/sql-pretty-printer.docs.md @@ -1,5 +1,5 @@ Format and beautify SQL queries with customizable styling options. This tool supports multiple SQL dialects including SQLite, PostgreSQL, and MySQL, allowing you to control indentation width, keyword capitalization, and indentation style. The formatted output can be easily copied to your clipboard with a single click. -<!-- topics: developer-tools, sqlite-databases --> +<!-- topics: sqlite-databases --> <!-- features: clipboard --> <!-- Generated from commit: 71a762dfc7190f764785b6246e8e17f4fa9a8ecd --> diff --git a/sqlite-ast.docs.md b/sqlite-ast.docs.md index 492a3420..ecf2a6f0 100644 --- a/sqlite-ast.docs.md +++ b/sqlite-ast.docs.md @@ -1,5 +1,5 @@ Parse SQLite SELECT queries into abstract syntax trees and view the results in JSON and Python representations. This tool uses the sqlite-ast library running in your browser via Pyodide to analyze SQL syntax and display both the dictionary-based parse tree and a rich pretty-printed representation. It supports complex queries including compound selects, common table expressions, and window functions, and can display partial parse results when encountering syntax errors. -<!-- topics: sqlite-databases, developer-tools --> +<!-- topics: sqlite-databases --> <!-- features: webassembly --> <!-- Generated from commit: 763e22bf8457c261a33c9a54e32322c6436d3faf --> diff --git a/sqlite-bytecode-explorer.docs.md b/sqlite-bytecode-explorer.docs.md index e8a05b80..09521694 100644 --- a/sqlite-bytecode-explorer.docs.md +++ b/sqlite-bytecode-explorer.docs.md @@ -1,5 +1,5 @@ Explore SQLite's Virtual Database Engine (VDBE) by analyzing the bytecode that SQLite generates when compiling SQL queries. This tool runs the `EXPLAIN` command on your SQL statements and annotates each instruction with detailed explanations of what it does, from cursor management and table scans to index lookups and aggregate functions. Use it to understand query execution strategies, identify optimization opportunities, and learn how SQLite's register-based virtual machine transforms SQL into low-level operations. -<!-- topics: sqlite-databases, developer-tools, reference-education --> +<!-- topics: sqlite-databases, reference-education --> <!-- features: webassembly --> <!-- Generated from commit: f1c84e9a1090b22667a95d19b5ac774ac903b1b1 --> diff --git a/sqlite-qrf.docs.md b/sqlite-qrf.docs.md index e772ff62..44c7e890 100644 --- a/sqlite-qrf.docs.md +++ b/sqlite-qrf.docs.md @@ -1,5 +1,5 @@ Format SQLite query results in 20 different styles including box-drawing tables, CSV, JSON, HTML, Markdown, and more using this interactive WebAssembly-based demonstration. Adjust formatting options like column headers, screen width, NULL display values, and border styles in real-time to see how your SQL queries render across all available output modes. The demo database includes sample tables for employees, products, and orders with pre-built example queries showcasing each formatting style. -<!-- topics: sqlite-databases, developer-tools --> +<!-- topics: sqlite-databases --> <!-- features: webassembly, clipboard, url-state --> <!-- Generated from commit: 94e4ddcc9b5fba8e6f714904dfb6ce4816e9d439 --> diff --git a/svg-render.docs.md b/svg-render.docs.md index 1aca66cc..412777ed 100644 --- a/svg-render.docs.md +++ b/svg-render.docs.md @@ -1,5 +1,5 @@ Convert SVG images to JPEG or PNG format with customizable dimensions, padding, and background colors. The tool allows you to paste SVG code directly, upload SVG files via drag-and-drop, or load SVG images from URLs, then instantly previews the converted result and provides download and base64 embedding options. URL hashes preserve your work for easy sharing and recovery. -<!-- topics: images-graphics, developer-tools --> +<!-- topics: images-graphics --> <!-- features: svg, canvas, file-upload, drag-and-drop, url-state, clipboard --> <!-- Generated from commit: aa44951cdb23b63465877c5f7787f09c83874276 --> diff --git a/swagger-subset.docs.md b/swagger-subset.docs.md index 6142dc47..1b5d0e02 100644 --- a/swagger-subset.docs.md +++ b/swagger-subset.docs.md @@ -1,5 +1,5 @@ Extract a subset of Swagger/OpenAPI definitions by selecting specific API endpoints and their dependencies. This tool parses a Swagger JSON document, displays all available paths and methods in an interactive checklist, and generates a filtered JSON output containing only the selected endpoints along with any referenced schema definitions they require. The generated subset can be copied to the clipboard for use in other applications or documentation. -<!-- topics: developer-tools, data-json --> +<!-- topics: data-json --> <!-- features: clipboard --> <!-- Generated from commit: 49277989809c8b6ca92e82ff82765d634b8400b2 --> diff --git a/syntaqlite.docs.md b/syntaqlite.docs.md index 98daf1ed..b48fc74c 100644 --- a/syntaqlite.docs.md +++ b/syntaqlite.docs.md @@ -2,6 +2,6 @@ Experiment with SQLite SQL parsing, formatting, validation, and tokenization directly in your browser using the syntaqlite parser. This interactive playground provides four main tools: a code formatter that restructures SQL with customizable options, a parser that generates abstract syntax trees, a validator that checks queries against a defined schema, and a tokenizer that breaks SQL into individual tokens with type classification. All processing happens client-side via Pyodide, which runs Python code in WebAssembly without requiring any server infrastructure. -<!-- topics: sqlite-databases, developer-tools --> +<!-- topics: sqlite-databases --> <!-- features: webassembly --> <!-- Generated from commit: d64e3f4d156aa46443e3ba886ed934416dbc1118 --> diff --git a/tacopy-playground.docs.md b/tacopy-playground.docs.md index 17113464..d724d568 100644 --- a/tacopy-playground.docs.md +++ b/tacopy-playground.docs.md @@ -1,5 +1,5 @@ Explore how tail-recursive Python functions are transformed into optimized iterative code using the Tacopy library. Enter your recursive function in the input panel to see the automatically generated transformed version, which eliminates stack overflow risks and improves performance by converting tail calls into loops. Try the built-in examples to understand how different recursive patterns are optimized. -<!-- topics: developer-tools, reference-education --> +<!-- topics: reference-education --> <!-- features: webassembly --> <!-- Generated from commit: 3af1ed845e36cfa53a161b3ce33406872057b9ea --> diff --git a/tags.json b/tags.json index 3f7f42c1..2cd10c8b 100644 --- a/tags.json +++ b/tags.json @@ -1,4 +1,31 @@ { + "categories": [ + { + "slug": "development", + "name": "Development & APIs", + "subcategories": ["developer-tools", "code-sandboxes", "apis-services", "css-layout", "encoding-security"] + }, + { + "slug": "data-ai", + "name": "Data, AI & Databases", + "subcategories": ["ai-llm", "data-json", "sqlite-databases", "data-visualization"] + }, + { + "slug": "media", + "name": "Images, Audio & Documents", + "subcategories": ["images-graphics", "audio-video", "documents-pdf"] + }, + { + "slug": "text-reference", + "name": "Text, Writing & Reference", + "subcategories": ["text-writing", "accessibility", "reference-education"] + }, + { + "slug": "web-life", + "name": "Web, Social & Fun", + "subcategories": ["social-feeds", "maps-geo", "productivity", "games-fun"] + } + ], "topics": { "ai-llm": "AI & LLMs", "text-writing": "Text & Writing", @@ -8,6 +35,8 @@ "maps-geo": "Maps & Geography", "css-layout": "CSS & Layout Playgrounds", "developer-tools": "Developer Tools", + "code-sandboxes": "Code Sandboxes & REPLs", + "apis-services": "Web APIs & Services", "data-visualization": "Data Visualization", "accessibility": "Accessibility", "sqlite-databases": "SQLite & Databases", diff --git a/terminal-to-html.docs.md b/terminal-to-html.docs.md index e9c4da82..e99c2beb 100644 --- a/terminal-to-html.docs.md +++ b/terminal-to-html.docs.md @@ -1,5 +1,5 @@ Convert terminal output into shareable HTML documents with support for colored text formatting. Paste terminal output in RTF, HTML, or plain text format, and the tool instantly generates clean HTML code ready for preview or export. Save your conversions as GitHub Gists for easy sharing and collaboration. -<!-- topics: developer-tools, text-writing --> +<!-- topics: text-writing --> <!-- features: clipboard, local-storage, fetch-network --> <!-- Generated from commit: 7b7a04fc224bbe0cec3fc00ce755273c2d6ae11d --> diff --git a/test_directory.py b/test_directory.py index 2e445007..c7a695f5 100644 --- a/test_directory.py +++ b/test_directory.py @@ -1,10 +1,27 @@ -"""Unit tests for the Yahoo-style directory renderer.""" +"""Unit tests for the Yahoo-style hierarchical directory renderer.""" import directory VOCAB = { - "topics": {"developer-tools": "Developer Tools", "games-fun": "Games & Fun"}, + "categories": [ + { + "slug": "development", + "name": "Development & APIs", + "subcategories": ["developer-tools", "code-sandboxes"], + }, + { + "slug": "web-life", + "name": "Web, Social & Fun", + "subcategories": ["games-fun", "maps-geo"], + }, + ], + "topics": { + "developer-tools": "Developer Tools", + "code-sandboxes": "Code Sandboxes & REPLs", + "games-fun": "Games & Fun", + "maps-geo": "Maps & Geography", + }, "features": {"clipboard": "Clipboard", "canvas": "Canvas"}, } @@ -20,36 +37,69 @@ "slug": "snake", "title": "Snake Game", "url": "/snake", - "topics": ["games-fun", "developer-tools"], + "topics": ["games-fun"], "features": ["canvas"], }, + { + "slug": "pyrepl", + "title": "Python REPL", + "url": "/pyrepl", + "topics": ["code-sandboxes"], + "features": [], + }, ] -def test_groups_tools_under_each_topic(): +def test_renders_top_level_categories_and_subcategories(): html = directory.render_directory(TOOLS, VOCAB) - # developer-tools has both tools; games-fun has one - assert "Developer Tools" in html - assert "Games & Fun" in html or "Games & Fun" in html - # json-diff: 1 topic (developer-tools) + 1 feature (clipboard) - assert html.count('href="/json-diff"') == 2 - # snake: 2 topics (games-fun, developer-tools) + 1 feature (canvas) - assert html.count('href="/snake"') == 3 + # Top-level category headings + assert 'id="cat-development"' in html + assert "Development & APIs" in html + # Subcategory headings under them + assert 'id="topic-developer-tools"' in html + assert 'id="topic-code-sandboxes"' in html -def test_counts_reflect_membership(): +def test_top_level_nav_links_to_categories(): html = directory.render_directory(TOOLS, VOCAB) - assert "Developer Tools" in html and "(2)" in html - assert "(1)" in html + assert 'href="#cat-development"' in html + assert 'href="#cat-web-life"' in html -def test_empty_categories_are_omitted(): +def test_empty_subcategories_are_omitted(): + # maps-geo has no tools -> should not render + html = directory.render_directory(TOOLS, VOCAB) + assert 'id="topic-maps-geo"' not in html + + +def test_empty_top_level_category_is_omitted(): vocab = { - "topics": {"developer-tools": "Developer Tools", "maps-geo": "Maps & Geography"}, - "features": {"clipboard": "Clipboard"}, + "categories": [ + {"slug": "empty", "name": "Empty Cat", "subcategories": ["maps-geo"]}, + {"slug": "development", "name": "Development", "subcategories": ["developer-tools"]}, + ], + "topics": {"developer-tools": "Developer Tools", "maps-geo": "Maps"}, + "features": {}, } html = directory.render_directory(TOOLS, vocab) - assert "Maps & Geography" not in html and "Maps & Geography" not in html + assert 'id="cat-empty"' not in html + assert "Empty Cat" not in html + + +def test_uncategorized_topics_fall_under_more(): + tools = TOOLS + [ + {"slug": "x", "title": "X", "url": "/x", "topics": ["mystery-tag"], "features": []} + ] + html = directory.render_directory(tools, VOCAB) + assert 'id="cat-more"' in html + assert 'href="/x"' in html + + +def test_feature_section_present_with_chips(): + html = directory.render_directory(TOOLS, VOCAB) + assert "Browse by browser feature" in html + assert 'href="#feature-clipboard"' in html + assert 'id="feature-canvas"' in html def test_escapes_titles(): @@ -65,10 +115,3 @@ def test_escapes_titles(): html = directory.render_directory(tools, VOCAB) assert "<script>" not in html assert "A & B" in html - - -def test_feature_section_present(): - html = directory.render_directory(TOOLS, VOCAB) - assert "Browse by browser feature" in html - assert "Clipboard" in html - assert "Canvas" in html diff --git a/text-diff.docs.md b/text-diff.docs.md index 5c7a60a4..2de27677 100644 --- a/text-diff.docs.md +++ b/text-diff.docs.md @@ -1,4 +1,4 @@ Compare two blocks of text to identify character-level differences between them. This tool uses a dynamic programming algorithm to compute the longest common subsequence and highlights removed text in red and added text in green for easy visualization of changes. The results are displayed character-by-character in a dedicated output section that clearly indicates what was deleted from the original text and what was inserted in the modified version. -<!-- topics: text-writing, developer-tools --> +<!-- topics: text-writing --> <!-- Generated from commit: b3c628b84c5c6a3b7fcfff10aa5de98b7f5d6962 --> diff --git a/tiff-orientation.docs.md b/tiff-orientation.docs.md index 66ef4a62..68a8709e 100644 --- a/tiff-orientation.docs.md +++ b/tiff-orientation.docs.md @@ -1,5 +1,5 @@ Read TIFF orientation metadata from JPEG images by uploading or dragging files into the drop zone. The tool parses the EXIF data embedded in the image file to extract the orientation tag, which indicates how the image should be displayed (normal, rotated 90° clockwise, rotated 180°, or rotated 270° clockwise). Debug information shows the file analysis process, including EXIF location, endianness detection, and TIFF header validation. -<!-- topics: images-graphics, developer-tools --> +<!-- topics: images-graphics --> <!-- features: file-upload, drag-and-drop --> <!-- Generated from commit: 9b6cdd52381f1acf2c1148ed23478da1ce1f199f --> diff --git a/turbo-pascal-deconstructed.docs.md b/turbo-pascal-deconstructed.docs.md index dd4d486e..07cedeb1 100644 --- a/turbo-pascal-deconstructed.docs.md +++ b/turbo-pascal-deconstructed.docs.md @@ -1,4 +1,4 @@ Explore an interactive breakdown of Turbo Pascal 3.02A's 39,731-byte executable, mapping each function from the header and display system through the parser and symbol table. Navigate the binary segments with an overhead visualization and detailed hex dumps with annotated disassembly, revealing how a complete compiler, editor, and runtime fit within the constraints of 1986 DOS memory while routing all file I/O through a single INT 21h dispatcher gateway. -<!-- topics: reference-education, developer-tools --> +<!-- topics: reference-education --> <!-- Generated from commit: b0e0ad77b9ac19eb0074f122fbb7f41e67b941ae --> diff --git a/unicode-binary-search.docs.md b/unicode-binary-search.docs.md index 2acf54e2..ff670fc1 100644 --- a/unicode-binary-search.docs.md +++ b/unicode-binary-search.docs.md @@ -1,5 +1,5 @@ View Unicode characters and their properties through an interactive binary search algorithm that makes real HTTP Range requests to fetch individual records from a binary database. Enter a character or Unicode codepoint to see each step of the search visualized in a network log, including fetch times and comparisons. The tool supports both standard binary search and interpolation search, which estimates the target's position based on codepoint values rather than always splitting the middle, potentially reducing the number of network requests needed. -<!-- topics: reference-education, developer-tools --> +<!-- topics: reference-education --> <!-- features: fetch-network --> <!-- Generated from commit: 0beead964c12f300b6484a0126cb89cfe928a2ee --> diff --git a/unix-timestamp.docs.md b/unix-timestamp.docs.md index 039bb251..a0516cc6 100644 --- a/unix-timestamp.docs.md +++ b/unix-timestamp.docs.md @@ -1,4 +1,4 @@ Convert Unix timestamps to human-readable dates and times with this tool. Enter a Unix timestamp (in seconds or milliseconds) to instantly view the corresponding date and time in both UTC and your local timezone. The converter automatically handles both 10-digit and 13-digit timestamps, making it easy to work with timestamps from various sources and systems. -<!-- topics: developer-tools, productivity --> +<!-- topics: productivity --> <!-- Generated from commit: 9c103673bb7d2f393911d7f81cfc29c16d160b53 --> diff --git a/v86.docs.md b/v86.docs.md index cfaf82ce..5002973a 100644 --- a/v86.docs.md +++ b/v86.docs.md @@ -1,5 +1,5 @@ Run Linux commands in your browser using x86 emulation powered by v86, a JavaScript/WebAssembly-based x86 emulator. This tool executes a minimal Buildroot Linux distribution directly in your browser, with typical boot times between 10-30 seconds depending on your device and connection speed. Enter commands in the input field to interact with the Linux shell and view output in the terminal window. -<!-- topics: developer-tools --> +<!-- topics: code-sandboxes --> <!-- features: webassembly, canvas --> <!-- Generated from commit: e8a68e36c67b2969215d9184ccba2b446c2f5314 --> diff --git a/xml-validator.docs.md b/xml-validator.docs.md index 28ba65d7..db7b9e92 100644 --- a/xml-validator.docs.md +++ b/xml-validator.docs.md @@ -1,4 +1,4 @@ Check XML documents for well-formedness by pasting content into the input area and clicking the validate button. The tool parses the XML and displays any syntax errors with precise line and column information, highlighting the problematic line in the code view below. -<!-- topics: developer-tools, data-json --> +<!-- topics: data-json --> <!-- Generated from commit: 8c49c1a81f9cf0673bcd8d20c30fc929c18909b6 --> diff --git a/yaml-explorer.docs.md b/yaml-explorer.docs.md index 1517127e..b459cb18 100644 --- a/yaml-explorer.docs.md +++ b/yaml-explorer.docs.md @@ -1,5 +1,5 @@ Parse and visualize YAML files in an interactive tree format with collapsible sections for easy navigation of nested data structures. Enter YAML content directly or load from a URL, then explore the data by expanding and collapsing individual elements. The tool preserves your navigation state in the URL, allowing you to share links with specific sections already expanded. -<!-- topics: data-json, developer-tools --> +<!-- topics: data-json --> <!-- features: fetch-network, url-state --> <!-- Generated from commit: ee48769f1bf8e56cad82db5a9207ca668f291162 --> diff --git a/youtube-thumbnails.docs.md b/youtube-thumbnails.docs.md index e65d5056..0a781602 100644 --- a/youtube-thumbnails.docs.md +++ b/youtube-thumbnails.docs.md @@ -1,5 +1,5 @@ View YouTube video thumbnails in multiple resolutions by entering a video URL or ID. This tool extracts and displays all available thumbnail formats from YouTube's image server, allowing you to preview different quality options and copy direct image links. Click on any thumbnail to expand it for a closer look, and use the copy button to save the image URL to your clipboard. -<!-- topics: developer-tools --> +<!-- topics: apis-services --> <!-- features: clipboard, url-state --> <!-- Generated from commit: 8d67d6ca349fdb27f0287cfd388b9a5485cd88b5 --> From 49129a20d45748373efa51ab80b943e77a386e50 Mon Sep 17 00:00:00 2001 From: Jesse Vincent <jesse@fsck.com> Date: Fri, 5 Jun 2026 15:34:21 -0700 Subject: [PATCH 6/7] Render the directory in classic Yahoo style Add a compact two-column category index (bold category names with inline subcategory links and tool counts), with the full per-category tool listings beneath it. --- build_index.py | 38 ++++++++++++++++++ directory.py | 99 ++++++++++++++++++++++++++++++----------------- test_directory.py | 16 ++++++-- 3 files changed, 114 insertions(+), 39 deletions(-) diff --git a/build_index.py b/build_index.py index c4d59fee..2ebd0e37 100755 --- a/build_index.py +++ b/build_index.py @@ -380,6 +380,44 @@ def build_index() -> None: padding: 4px 10px; margin: 1.5em 0 0.9em; border-radius: 2px; + scroll-margin-top: 8px; + }} + .yh-index {{ + column-width: 330px; + column-gap: 44px; + margin: 0.5em 0 1em; + }} + .yh-cat {{ + break-inside: avoid; + -webkit-column-break-inside: avoid; + display: inline-block; + width: 100%; + margin: 0 0 1.1em; + vertical-align: top; + }} + .yh-cat h3 {{ + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.1em; + margin: 0 0 0.15em; + }} + .yh-cat h3 a {{ + color: #4a2f63; + font-weight: bold; + }} + .yh-xtra {{ + color: #cc0000; + font-size: 0.7em; + font-weight: normal; + vertical-align: super; + }} + .yh-cat p {{ + margin: 0; + font-size: 0.9em; + line-height: 1.45; + color: #555; + }} + .dir-cat h3 {{ + scroll-margin-top: 8px; }} .dir-chips {{ display: flex; diff --git a/directory.py b/directory.py index acce6ea6..6b238f0f 100644 --- a/directory.py +++ b/directory.py @@ -46,54 +46,81 @@ def _grid(blocks: Sequence[str]) -> str: return '<div class="dir-grid">\n' + "\n".join(blocks) + "\n</div>" -def _render_topics(tools: Sequence[dict], vocab: dict) -> str: +def _collect_categories(tools: Sequence[dict], vocab: dict): + """Return ``[(category, [(sub_slug, sub_display, members), ...]), ...]``. + + Categories and subcategories with no tools are dropped. Any topic tag not + assigned to a category (e.g. newly coined) is gathered under a "More" + category at the end. + """ buckets = _bucket(tools, "topics") topics_map = vocab.get("topics", {}) - categories = list(vocab.get("categories", [])) - placed = set() - sections = [] - nav_links = [] + collected = [] - def emit_category(cat_slug, cat_name, sub_slugs): - blocks = [] - for sub in sub_slugs: + for cat in vocab.get("categories", []): + subs = [] + for sub in cat.get("subcategories", []): + placed.add(sub) members = buckets.get(sub) - if not members: - continue - blocks.append( - _subcat_block(f"topic-{sub}", _display(topics_map, sub), members) - ) - if not blocks: - return - nav_links.append( - f'<a href="#cat-{html.escape(cat_slug)}">{html.escape(cat_name)}</a>' + if members: + subs.append((sub, _display(topics_map, sub), members)) + if subs: + collected.append((cat, subs)) + + leftover = sorted(slug for slug in buckets if slug not in placed) + if leftover: + more = {"slug": "more", "name": "More"} + subs = [(s, _display(topics_map, s), buckets[s]) for s in leftover] + collected.append((more, subs)) + + return collected + + +def _render_index(collected) -> str: + """Render the compact Yahoo-style two-column category index.""" + entries = [] + for cat, subs in collected: + cat_slug = html.escape(cat.get("slug", "")) + cat_name = html.escape(cat.get("name", "")) + total = sum(len(m) for _, _, m in subs) + sub_links = ", ".join( + f'<a href="#topic-{html.escape(slug)}">{html.escape(display)}</a>' + for slug, display, _ in subs ) - sections.append( - f'<h3 class="dir-toplevel" id="cat-{html.escape(cat_slug)}">' - f"{html.escape(cat_name)}</h3>\n" + _grid(blocks) + entries.append( + f""" <div class="yh-cat"> + <h3><a href="#cat-{cat_slug}">{cat_name}</a> <span class="yh-xtra">[{total}]</span></h3> + <p>{sub_links}</p> + </div>""" ) + return '<div class="yh-index">\n' + "\n".join(entries) + "\n</div>" - for cat in categories: - sub_slugs = cat.get("subcategories", []) - placed.update(sub_slugs) - emit_category(cat.get("slug", ""), cat.get("name", ""), sub_slugs) - # Any topic tag not assigned to a category (e.g. newly coined) lands here. - leftover = [slug for slug in buckets if slug not in placed] - if leftover: - emit_category("more", "More", sorted(leftover)) +def _render_detail(collected) -> str: + """Render the full per-category tool listings beneath the index.""" + sections = [] + for cat, subs in collected: + cat_slug = html.escape(cat.get("slug", "")) + cat_name = html.escape(cat.get("name", "")) + blocks = [ + _subcat_block(f"topic-{slug}", display, members) + for slug, display, members in subs + ] + sections.append( + f'<h3 class="dir-toplevel" id="cat-{cat_slug}">{cat_name}</h3>\n' + + _grid(blocks) + ) + return "\n".join(sections) - nav = ( - '<div class="dir-nav">' + " · ".join(nav_links) + "</div>" - if nav_links - else "" - ) + +def _render_topics(tools: Sequence[dict], vocab: dict) -> str: + collected = _collect_categories(tools, vocab) return ( '<h2 class="dir-heading">Browse by category</h2>\n' - + nav - + "\n" - + "\n".join(sections) + + _render_index(collected) + + '\n<h2 class="dir-heading">All tools by category</h2>\n' + + _render_detail(collected) ) diff --git a/test_directory.py b/test_directory.py index c7a695f5..22589b8f 100644 --- a/test_directory.py +++ b/test_directory.py @@ -52,7 +52,7 @@ def test_renders_top_level_categories_and_subcategories(): html = directory.render_directory(TOOLS, VOCAB) - # Top-level category headings + # Top-level category headings (in the detail listing) assert 'id="cat-development"' in html assert "Development & APIs" in html # Subcategory headings under them @@ -60,10 +60,20 @@ def test_renders_top_level_categories_and_subcategories(): assert 'id="topic-code-sandboxes"' in html -def test_top_level_nav_links_to_categories(): +def test_yahoo_index_lists_categories_with_inline_subcategory_links(): html = directory.render_directory(TOOLS, VOCAB) + assert 'class="yh-index"' in html + # Category name links to its detail section assert 'href="#cat-development"' in html - assert 'href="#cat-web-life"' in html + # Subcategories appear as inline links into their tool listings + assert 'href="#topic-developer-tools"' in html + assert 'href="#topic-code-sandboxes"' in html + + +def test_index_shows_tool_count_per_category(): + html = directory.render_directory(TOOLS, VOCAB) + # development has json-diff (developer-tools) + pyrepl (code-sandboxes) = 2 + assert "[2]" in html def test_empty_subcategories_are_omitted(): From 43d9fde6506715d641e30515c6fee25d9a82ef51 Mon Sep 17 00:00:00 2001 From: Jesse Vincent <jesse@fsck.com> Date: Fri, 5 Jun 2026 15:43:44 -0700 Subject: [PATCH 7/7] Add standalone category pages; homepage shows index only - Homepage now shows only the Yahoo-style 'Browse by category' index; each subcategory links to its own standalone page. - New build_categories.py generates a 'All tools by category' page (full hierarchy + browse-by-feature) and one page per subcategory (breadcrumb + tools with descriptions). - Extract shared chrome/directory CSS into page_template.py, used by both the homepage and the category pages (de-dups the styles). - Wire build_categories.py into build.sh; gitignore the generated pages. --- .gitignore | 2 + build.sh | 3 + build_categories.py | 50 +++++++ build_index.py | 323 ++++++++------------------------------------ directory.py | 162 +++++++++++++--------- page_template.py | 255 ++++++++++++++++++++++++++++++++++ test_directory.py | 114 +++++++++------- 7 files changed, 529 insertions(+), 380 deletions(-) create mode 100644 build_categories.py create mode 100644 page_template.py diff --git a/.gitignore b/.gitignore index 58ff2d5f..78f6c696 100644 --- a/.gitignore +++ b/.gitignore @@ -3,6 +3,8 @@ gathered_links.json colophon.html index.html by-month.html +categories.html +category-*.html *.egg-info/ __pycache__/ diff --git a/build.sh b/build.sh index cd6ca5ac..f4a3cfd5 100755 --- a/build.sh +++ b/build.sh @@ -26,6 +26,9 @@ python build_dates.py echo "Building index page..." python build_index.py +echo "Building category pages..." +python build_categories.py + echo "Building by-month page..." python build_by_month.py diff --git a/build_categories.py b/build_categories.py new file mode 100644 index 00000000..d02f3a37 --- /dev/null +++ b/build_categories.py @@ -0,0 +1,50 @@ +#!/usr/bin/env python3 +"""Generate the 'All tools by category' page and one page per subcategory.""" + +from __future__ import annotations + +import json +from pathlib import Path + +import directory +import page_template +import tags_lib + +TOOLS_JSON_PATH = Path("tools.json") + + +def _load_tools(): + if not TOOLS_JSON_PATH.exists(): + return [] + with TOOLS_JSON_PATH.open("r", encoding="utf-8") as fp: + return json.load(fp) + + +def build_categories() -> None: + tools = _load_tools() + vocab = tags_lib.load_vocabulary() + + # The combined "All tools by category" page. + all_body = directory.render_all_page_body(tools, vocab) + Path("categories.html").write_text( + page_template.render_page("All tools by category", all_body), "utf-8" + ) + + # One standalone page per (non-empty) subcategory. + count = 0 + for cat, subs in directory.collect_categories(tools, vocab): + for slug, display, members in subs: + body = directory.render_subcategory_body( + slug, display, members, cat.get("name", "") + ) + title = f"{display} — tools.simonwillison.net" + Path(directory.subcategory_filename(slug)).write_text( + page_template.render_page(title, body), "utf-8" + ) + count += 1 + + print(f"Built categories.html and {count} subcategory pages") + + +if __name__ == "__main__": + build_categories() diff --git a/build_index.py b/build_index.py index 2ebd0e37..68d2d489 100755 --- a/build_index.py +++ b/build_index.py @@ -9,6 +9,7 @@ from typing import Iterable, List, Sequence import directory +import page_template import tags_lib try: @@ -192,124 +193,62 @@ def build_index() -> None: body_html = recent_section_html + body_html body_html = body_html + '\n' + directory_html - full_html = f"""<!DOCTYPE html> -<html lang="en"> -<head> - <meta charset="UTF-8"> - <meta name="viewport" content="width=device-width, initial-scale=1.0"> - <title>tools.simonwillison.net - - - - -
-{body_html} -
+ } +""" + + settings_html = '''

Settings

-
- - - -""" + } + }); +})(); +""" + + full_html = page_template.render_page( + title="tools.simonwillison.net", + body_html=body_html + "\n" + settings_html, + extra_css=settings_css, + body_extra=toggle_script, + ) OUTPUT_PATH.write_text(full_html, "utf-8") print("index.html created successfully") diff --git a/directory.py b/directory.py index 6b238f0f..27f80fe7 100644 --- a/directory.py +++ b/directory.py @@ -1,10 +1,9 @@ -"""Render a classic Yahoo-style directory of tools. +"""Render the classic Yahoo-style tool directory. -The directory has two levels: top-level categories (e.g. "Development & APIs") -each containing subcategories (e.g. "Developer Tools", "Code Sandboxes & REPLs"), -with the tools listed under each subcategory. A second section groups tools by -the browser feature they use. The output is static HTML that works with no -JavaScript; feature chips are anchor links into the feature section. +The homepage shows a compact two-level category index (top-level categories with +their subcategories as inline links). Each subcategory links to its own standalone +page listing the tools; a single "All tools by category" page shows the whole +hierarchy plus a browse-by-browser-feature section. """ from __future__ import annotations @@ -13,6 +12,16 @@ from collections import defaultdict from typing import Dict, List, Sequence +ALL_URL = "/categories" + + +def subcategory_filename(slug: str) -> str: + return f"category-{slug}.html" + + +def subcategory_url(slug: str) -> str: + return f"/category-{slug}" + def _bucket(tools: Sequence[dict], namespace: str) -> Dict[str, List[dict]]: """Group tools by each tag in the given namespace ('topics' or 'features').""" @@ -27,17 +36,27 @@ def _display(vocab_group: Dict[str, str], slug: str) -> str: return vocab_group.get(slug, slug.replace("-", " ").title()) -def _subcat_block(anchor: str, display: str, members: Sequence[dict]) -> str: - members = sorted(members, key=lambda t: t.get("title", "").lower()) - links = "\n".join( +def _sorted(members: Sequence[dict]) -> List[dict]: + return sorted(members, key=lambda t: t.get("title", "").lower()) + + +def _tool_links(members: Sequence[dict]) -> str: + return "\n".join( f'
  • ' f'{html.escape(tool.get("title", tool.get("slug", "")))}
  • ' - for tool in members + for tool in _sorted(members) + ) + + +def _subcat_block(slug: str, display: str, members: Sequence[dict]) -> str: + heading = ( + f'{html.escape(display)} ' + f'({len(members)})' ) - return f"""
    -

    {html.escape(display)} ({len(members)})

    + return f"""
    +

    {heading}

      -{links} +{_tool_links(members)}
    """ @@ -46,12 +65,11 @@ def _grid(blocks: Sequence[str]) -> str: return '
    \n' + "\n".join(blocks) + "\n
    " -def _collect_categories(tools: Sequence[dict], vocab: dict): +def collect_categories(tools: Sequence[dict], vocab: dict): """Return ``[(category, [(sub_slug, sub_display, members), ...]), ...]``. - Categories and subcategories with no tools are dropped. Any topic tag not - assigned to a category (e.g. newly coined) is gathered under a "More" - category at the end. + Categories and subcategories with no tools are dropped. Topic tags not + assigned to any category are gathered under a "More" category at the end. """ buckets = _bucket(tools, "topics") topics_map = vocab.get("topics", {}) @@ -77,80 +95,96 @@ def _collect_categories(tools: Sequence[dict], vocab: dict): return collected -def _render_index(collected) -> str: - """Render the compact Yahoo-style two-column category index.""" +def render_index(tools: Sequence[dict], vocab: dict) -> str: + """Render the homepage category index (top-level categories + inline subs).""" + collected = collect_categories(tools, vocab) entries = [] for cat, subs in collected: cat_slug = html.escape(cat.get("slug", "")) cat_name = html.escape(cat.get("name", "")) total = sum(len(m) for _, _, m in subs) sub_links = ", ".join( - f'{html.escape(display)}' + f'{html.escape(display)}' for slug, display, _ in subs ) entries.append( f"""
    -

    {cat_name} [{total}]

    +

    {cat_name} [{total}]

    {sub_links}

    """ ) - return '
    \n' + "\n".join(entries) + "\n
    " + return ( + '
    \n' + '

    Browse by category

    \n' + '
    \n' + "\n".join(entries) + "\n
    \n" + f'\n' + "
    " + ) -def _render_detail(collected) -> str: - """Render the full per-category tool listings beneath the index.""" +def _render_features(tools: Sequence[dict], vocab: dict) -> str: + buckets = _bucket(tools, "features") + features_map = vocab.get("features", {}) + ordered = [slug for slug in features_map if buckets.get(slug)] + ordered += [slug for slug in buckets if slug not in features_map] + + blocks = [] + for slug in ordered: + members = buckets[slug] + blocks.append( + f"""
    +

    {html.escape(_display(features_map, slug))} ({len(members)})

    +
      +{_tool_links(members)} +
    +
    """ + ) + return ( + '

    Browse by browser feature

    \n' + _grid(blocks) + ) + + +def render_all_page_body(tools: Sequence[dict], vocab: dict) -> str: + """Render the body of the standalone 'All tools by category' page.""" + collected = collect_categories(tools, vocab) sections = [] for cat, subs in collected: cat_slug = html.escape(cat.get("slug", "")) cat_name = html.escape(cat.get("name", "")) - blocks = [ - _subcat_block(f"topic-{slug}", display, members) - for slug, display, members in subs - ] + blocks = [_subcat_block(slug, display, members) for slug, display, members in subs] sections.append( - f'

    {cat_name}

    \n' - + _grid(blocks) + f'

    {cat_name}

    \n' + _grid(blocks) ) - return "\n".join(sections) - - -def _render_topics(tools: Sequence[dict], vocab: dict) -> str: - collected = _collect_categories(tools, vocab) return ( - '

    Browse by category

    \n' - + _render_index(collected) - + '\n

    All tools by category

    \n' - + _render_detail(collected) + '\n' + "

    All tools by category

    \n" + '
    \n' + + "\n".join(sections) + + "\n" + + _render_features(tools, vocab) + + "\n
    " ) -def _render_features(tools: Sequence[dict], vocab: dict) -> str: - buckets = _bucket(tools, "features") - features_map = vocab.get("features", {}) - ordered = [slug for slug in features_map if buckets.get(slug)] - ordered += [slug for slug in buckets if slug not in features_map] - - chips = "\n".join( - f' ' - f'{html.escape(_display(features_map, slug))} ' - f'({len(buckets[slug])})' - for slug in ordered +def render_subcategory_body(slug: str, display: str, members: Sequence[dict], cat_name: str) -> str: + """Render the body of a single subcategory page.""" + items = "\n".join( + f'
  • {html.escape(t.get("title", t.get("slug", "")))}' + + ( + f'\n

    {html.escape(t.get("description", ""))}

    ' + if t.get("description") + else "" + ) + + "
  • " + for t in _sorted(members) ) - blocks = [ - _subcat_block(f"feature-{slug}", _display(features_map, slug), buckets[slug]) - for slug in ordered - ] return ( - '

    Browse by browser feature

    \n' - f'
    \n{chips}\n
    \n' + _grid(blocks) + '\n' + f"

    {html.escape(display)} ({len(members)})

    \n" + f'' ) -def render_directory(tools: Sequence[dict], vocab: dict) -> str: - """Render the full directory HTML fragment from tools and the tag vocabulary.""" - return f"""
    -

    A classic directory of every tool, sorted into categories. -Pick a category below, or jump to the browser features a tool uses.

    -{_render_topics(tools, vocab)} -{_render_features(tools, vocab)} -
    """ +# Backwards-compatible alias used by build_index. +render_directory = render_index diff --git a/page_template.py b/page_template.py new file mode 100644 index 00000000..af508d0a --- /dev/null +++ b/page_template.py @@ -0,0 +1,255 @@ +"""Shared HTML chrome for generated pages (homepage, category pages). + +Centralises the base + navigation + directory CSS so the homepage and the +category pages stay visually consistent without duplicating styles. +""" + +from __future__ import annotations + +STYLE = """ + body { + font-family: "Helvetica Neue", helvetica, sans-serif; + line-height: 1.4; + margin: 0; + padding: 0; + } + h1 { + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.4em; + } + h2 { + margin-top: 1.5em; + } + a { + color: #0066cc; + text-decoration: none; + } + a:hover { + text-decoration: underline; + } + code { + background-color: rgba(27,31,35,0.05); + border-radius: 3px; + padding: 0.2em 0.4em; + } + nav { + text-align: left; + background: linear-gradient(to bottom, rgb(154, 103, 175) 0%, rgb(96, 72, 129) 49%, rgb(100, 67, 130) 100%); + color: white; + } + nav p { + display: flex; + justify-content: space-between; + margin: 0; + padding: 4px 2em; + } + nav a:link, + nav a:visited, + nav a:hover, + nav a:focus, + nav a:active { + color: white; + text-decoration: none; + } + section.body { + padding: 0.5em 2em; + max-width: 800px; + } + @media (max-width: 600px) { + section.body { + padding: 0em 1em; + } + nav p { + padding: 4px 1em; + } + } + html { + scroll-behavior: smooth; + } + .breadcrumb { + font-size: 0.9em; + color: #777; + margin: 0.5em 0 1em; + } + .directory { + margin-top: 1em; + } + .dir-intro { + color: #444; + font-size: 0.95em; + max-width: 48em; + margin: 0.5em 0 1em; + } + .dir-heading { + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.35em; + color: #4a2f63; + border-bottom: 2px solid #9a67af; + padding-bottom: 2px; + margin: 1.4em 0 0.8em; + } + .dir-toplevel { + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.1em; + color: #fff; + background: linear-gradient(to bottom, rgb(154, 103, 175) 0%, rgb(100, 67, 130) 100%); + padding: 4px 10px; + margin: 1.5em 0 0.9em; + border-radius: 2px; + scroll-margin-top: 8px; + } + .dir-toplevel a { color: #fff; } + .yh-index { + column-width: 330px; + column-gap: 44px; + margin: 0.5em 0 1em; + } + .yh-cat { + break-inside: avoid; + -webkit-column-break-inside: avoid; + display: inline-block; + width: 100%; + margin: 0 0 1.1em; + vertical-align: top; + } + .yh-cat h3 { + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.1em; + margin: 0 0 0.15em; + } + .yh-cat h3 a { + color: #4a2f63; + font-weight: bold; + } + .yh-xtra { + color: #cc0000; + font-size: 0.7em; + font-weight: normal; + vertical-align: super; + } + .yh-cat p { + margin: 0; + font-size: 0.9em; + line-height: 1.45; + color: #555; + } + .browse-all-link { + margin: 0.5em 0 0; + font-size: 0.95em; + } + .dir-chips { + display: flex; + flex-wrap: wrap; + gap: 6px; + margin: 0 0 1.5em; + } + .dir-chip { + font-size: 0.82em; + background: #f0ebf5; + border: 1px solid #d3c4e0; + border-radius: 3px; + padding: 2px 8px; + color: #5a3d73 !important; + white-space: nowrap; + } + .dir-chip:hover { + background: #5a3d73; + color: #fff !important; + text-decoration: none; + } + .dir-grid { + column-width: 280px; + column-gap: 30px; + } + .dir-cat { + break-inside: avoid; + -webkit-column-break-inside: avoid; + display: inline-block; + width: 100%; + margin: 0 0 1.4em; + vertical-align: top; + } + .dir-cat h3 { + font-family: Georgia, 'Times New Roman', Times, serif; + font-size: 1.05em; + font-weight: bold; + margin: 0 0 0.3em; + padding-bottom: 2px; + border-bottom: 1px solid #c9b8d6; + color: #5a3d73; + scroll-margin-top: 8px; + } + .dir-cat ul { + list-style: none; + margin: 0; + padding: 0; + } + .dir-cat li { + font-size: 0.9em; + line-height: 1.5; + padding-left: 0.9em; + text-indent: -0.9em; + } + .dir-cat li::before { + content: "\\203A"; + color: #b8a3c9; + margin-right: 0.4em; + } + .dir-count { + color: #999; + font-weight: normal; + font-size: 0.85em; + } + .tool-list { + list-style: none; + margin: 0; + padding: 0; + } + .tool-list li { + margin: 0 0 1em; + } + .tool-list a { + font-weight: bold; + } + .tool-list .tool-desc { + color: #444; + font-size: 0.92em; + margin: 0.15em 0 0; + } + :target > h3 { + background: #fdf6a8; + } +""" + +NAV = ( + '' +) + + +def render_page(title, body_html, extra_css="", body_extra=""): + """Render a complete HTML document with the shared chrome. + + ``extra_css`` is inserted after the shared style block; ``body_extra`` is + placed after the main section (e.g. for page-specific scripts). + """ + import html as _html + + return f""" + + + + + {_html.escape(title)} + + + +{NAV} +
    +{body_html} +
    +{body_extra} + + +""" diff --git a/test_directory.py b/test_directory.py index 22589b8f..8b8ba40b 100644 --- a/test_directory.py +++ b/test_directory.py @@ -1,4 +1,4 @@ -"""Unit tests for the Yahoo-style hierarchical directory renderer.""" +"""Unit tests for the Yahoo-style directory renderer and category pages.""" import directory @@ -30,6 +30,7 @@ "slug": "json-diff", "title": "JSON Diff Tool", "url": "/json-diff", + "description": "Compare JSON documents side by side.", "topics": ["developer-tools"], "features": ["clipboard"], }, @@ -37,6 +38,7 @@ "slug": "snake", "title": "Snake Game", "url": "/snake", + "description": "Play snake.", "topics": ["games-fun"], "features": ["canvas"], }, @@ -44,84 +46,92 @@ "slug": "pyrepl", "title": "Python REPL", "url": "/pyrepl", + "description": "Run Python in the browser.", "topics": ["code-sandboxes"], "features": [], }, ] -def test_renders_top_level_categories_and_subcategories(): - html = directory.render_directory(TOOLS, VOCAB) - # Top-level category headings (in the detail listing) - assert 'id="cat-development"' in html +# --- Homepage index ------------------------------------------------------- + +def test_index_lists_categories_with_counts(): + html = directory.render_index(TOOLS, VOCAB) + assert 'class="yh-index"' in html assert "Development & APIs" in html - # Subcategory headings under them + assert "[2]" in html # developer-tools + code-sandboxes + + +def test_index_subcategories_link_to_standalone_pages(): + html = directory.render_index(TOOLS, VOCAB) + assert 'href="/category-developer-tools"' in html + assert 'href="/category-code-sandboxes"' in html + + +def test_index_category_links_to_all_page_anchor(): + html = directory.render_index(TOOLS, VOCAB) + assert 'href="/categories#cat-development"' in html + + +def test_index_has_browse_all_link(): + html = directory.render_index(TOOLS, VOCAB) + assert 'href="/categories"' in html + + +def test_index_omits_empty_subcategories(): + html = directory.render_index(TOOLS, VOCAB) + assert "category-maps-geo" not in html # maps-geo has no tools + + +# --- All-tools-by-category page ------------------------------------------ + +def test_all_page_has_category_sections_and_feature_section(): + html = directory.render_all_page_body(TOOLS, VOCAB) + assert 'id="cat-development"' in html assert 'id="topic-developer-tools"' in html - assert 'id="topic-code-sandboxes"' in html + assert "Browse by browser feature" in html + assert 'id="feature-clipboard"' in html -def test_yahoo_index_lists_categories_with_inline_subcategory_links(): - html = directory.render_directory(TOOLS, VOCAB) - assert 'class="yh-index"' in html - # Category name links to its detail section - assert 'href="#cat-development"' in html - # Subcategories appear as inline links into their tool listings - assert 'href="#topic-developer-tools"' in html - assert 'href="#topic-code-sandboxes"' in html +def test_all_page_subcategory_heading_links_to_page(): + html = directory.render_all_page_body(TOOLS, VOCAB) + assert 'href="/category-developer-tools"' in html -def test_index_shows_tool_count_per_category(): - html = directory.render_directory(TOOLS, VOCAB) - # development has json-diff (developer-tools) + pyrepl (code-sandboxes) = 2 - assert "[2]" in html +# --- Subcategory page ----------------------------------------------------- +def test_subcategory_body_lists_tools_with_descriptions(): + html = directory.render_subcategory_body( + "developer-tools", "Developer Tools", [TOOLS[0]], "Development & APIs" + ) + assert 'href="/json-diff"' in html + assert "Compare JSON documents side by side." in html + assert "breadcrumb" in html + assert "Development & APIs" in html -def test_empty_subcategories_are_omitted(): - # maps-geo has no tools -> should not render - html = directory.render_directory(TOOLS, VOCAB) - assert 'id="topic-maps-geo"' not in html +def test_subcategory_filename_and_url(): + assert directory.subcategory_filename("developer-tools") == "category-developer-tools.html" + assert directory.subcategory_url("developer-tools") == "/category-developer-tools" -def test_empty_top_level_category_is_omitted(): - vocab = { - "categories": [ - {"slug": "empty", "name": "Empty Cat", "subcategories": ["maps-geo"]}, - {"slug": "development", "name": "Development", "subcategories": ["developer-tools"]}, - ], - "topics": {"developer-tools": "Developer Tools", "maps-geo": "Maps"}, - "features": {}, - } - html = directory.render_directory(TOOLS, vocab) - assert 'id="cat-empty"' not in html - assert "Empty Cat" not in html +# --- Uncategorized topics ------------------------------------------------- def test_uncategorized_topics_fall_under_more(): tools = TOOLS + [ - {"slug": "x", "title": "X", "url": "/x", "topics": ["mystery-tag"], "features": []} + {"slug": "x", "title": "X", "url": "/x", "description": "", "topics": ["mystery-tag"], "features": []} ] - html = directory.render_directory(tools, VOCAB) + html = directory.render_all_page_body(tools, VOCAB) assert 'id="cat-more"' in html - assert 'href="/x"' in html + assert 'href="/category-mystery-tag"' in html -def test_feature_section_present_with_chips(): - html = directory.render_directory(TOOLS, VOCAB) - assert "Browse by browser feature" in html - assert 'href="#feature-clipboard"' in html - assert 'id="feature-canvas"' in html - +# --- Escaping ------------------------------------------------------------- def test_escapes_titles(): tools = [ - { - "slug": "x", - "title": "A & B