Changelog

Every update, documented. Major releases, new features, bug fixes, and improvements — all in one place.

Added Changed Fixed Removed
v3.3.0

Template-Driven Tool Generators - 7 New Categories, ~7,600 New Tools

Massive scale-up via the Image-Converters playbook: 7 new template-driven generators that emit one PHP shell per (from, to) pair, all sharing a single client-side engine + CSS. Total tool count went from 1,540 to 9,146 (5.94x). Each generator script lives in tools/_dev/ and is fully re-runnable - bump a list, rebuild, every PHP shell + the config.php registration block updates idempotently.

The build pattern: each tool gets its own URL, its own SEO-friendly metadata, and its own deep-linkable page, but shares the engine JS so disk cost is ~1 KB per tool and there are no per-tool runtime dependencies to load.

  • Unit Conversions (/category/unit-conversions) - 1,048 tools. Generated from tools/_dev/build-unit-converters.py across 16 unit categories: length (11 units), mass (9), volume (11), time (9), speed (6), area (9), energy (9), power (6), pressure (9), force (6), frequency (6), angle (7), temperature (5 - special-case scales), data storage (14, decimal + binary), density (7), cooking (7). Each tool: bidirectional input pair, formula caption, quick-value chips, copy button, related-converter chips. Shared unit-converter.js handles linear conversions and Celsius / Fahrenheit / Kelvin / Rankine / Reaumur math.
  • Color Converters (/category/color-converters) - 90 tools. All 10x9 ordered pairs across HEX / RGB / HSL / HSV / CMYK / LAB / LCH / XYZ / OKLab / OKLCH. Shared engine via color-converter.js - all conversions route through sRGB or XYZ as a hub, with proper sRGB ↔ linear gamma + D65-relative XYZ matrix + spec-correct OKLab math (Bjorn Ottosson). Every tool has a click-to-pick colour swatch (opens the browser's native colour picker) and 8 quick-colour chips.
  • Text Codecs (/category/text-codecs) - 30 tools. Base32 / Base58 / Base85 encoders + decoders, hex / binary / octal text codecs, URL component encode/decode, HTML entity decoder, Atbash, Caesar (with shift parameter), Morse decoder (encoder already existed), Braille encoder + decoder, A1Z26 encoder + decoder, NATO phonetic alphabet, reverse text, Pig Latin, leet (1337) speak, upside-down text, Unicode escape encoder + decoder. Pure JS, single shared engine text-codec.js - no external deps.
  • Number Systems (/category/number-systems) - 42 tools. All ordered pairs across decimal / binary / octal / hex / Roman numerals / English words / scientific notation. Roman supports 1-3,999. English handles 0 to 999 trillion. Pure JS engine number-system.js.
  • Numeric Bases (/category/numeric-bases) - 1,190 tools. All 35x34 ordered pairs across bases 2 through 36. Single shared engine numeric-base.js - parseInt / toString do all the work for these.
  • Currency Converters (/category/currency-converters) - 2,450 tools across 50 major fiat currencies (USD / EUR / GBP / JPY / CHF / CAD / AUD / CNY / HKD / SGD / INR / KRW / MXN / BRL / NZD + 35 more covering all major regions). Live rates from frankfurter.app (ECB-backed) with open.er-api.com as automatic fallback. Rates cached in sessionStorage for 1 hour to spare the APIs. Per-page rate display showing source + date. Both directions live - typing into either side computes the other.
  • Timezone Converters (/category/timezone-converters) - 2,756 tools across 53 major cities + UTC: Americas (NYC, LA, Chicago, Denver, Phoenix, Toronto, Vancouver, Mexico City, Sao Paulo, Buenos Aires, Lima, Bogota, Santiago, Caracas), Europe (London, Dublin, Paris, Berlin, Madrid, Rome, Lisbon, Amsterdam, Vienna, Warsaw, Prague, Athens, Istanbul, Moscow, Helsinki, Stockholm), Africa / Middle East (Cairo, Johannesburg, Lagos, Nairobi, Dubai, Riyadh, Tehran), Asia (Mumbai, Karachi, Dhaka, Bangkok, Jakarta, Singapore, Manila, Hong Kong, Shanghai, Taipei, Seoul, Tokyo), Pacific (Sydney, Auckland, Honolulu). All DST-aware via Intl.DateTimeFormat + the browser's IANA tz database. Live offset display + difference indicator on every page.
  • Generator infrastructure - 5 build scripts under tools/_dev/: build-unit-converters.py, build-color-converters.py, build-text-codecs.py, build-phase-c.py (number / currency / timezone), build-numeric-bases.py. Each is idempotent - re-running strips the old category block from config.php and writes a fresh one. Shared patch_config() regex inserts before the closing ]; of the getCategories() array. Shared engine + CSS files live under assets/{js,css}/tools/.
  • PHP-side architecture stress at 9K tools - config.php ballooned to 1.6 MB and PHP load time per request hit ~50 ms. Still acceptable, but the next push (toward 30K+) requires splitting registration to per-category JSON files in tools/_meta/ with lazy getCategories() loading. Refactor planned next ship.
  • Three new shared CSS engines (unit-converter.css, color-converter.css, text-codec.css, number-system.css) all follow the same pattern: paired input columns, swap arrow, formula / rate / info bar, related-tool chip row, mobile collapse-to-vertical at 600 px. :has(.uc), :has(.cc), :has(.ec), :has(.ns / .cv / .tz), :has(.bc) selectors override .ub-tool-layout's 2-col grid for these single-pane tools.
  • Naming-conflict near-misses caught early - existing site already had encoding-converter and base-converter tools, so the new shared engines were renamed to text-codec.js and numeric-base.js respectively to avoid colliding with tool.php's slug-keyed JS auto-loader.
  • Currency cascade hardening - frankfurter.app only covers ~33 currencies; for pairs involving any of the other 17, the engine now correctly falls through to open.er-api.com (which covers 150+) without showing an error to the user. Cache-buster query string (?_=<ts><rand>) appended to every fetch so soft-reload never serves a stale cached error.
v3.2.0

Networking Tools, Monaco Code Editor, Two Max-Strength Obfuscators, Paste-Drop Rebuild

Biggest release since v3.0. A whole new category, a full VS Code-grade editor, two industrial-strength obfuscators with hand-rolled confusable-character renaming, and a complete redesign of the paste-to-router as a drop-target FAB with handoff into target tools. Every new tool is 100% client-side except where physically impossible (real distributed traceroutes need real probes — so we wired in globalping.io and check-host.net for that).

  • New category: Networking (10 tools registered, 7 built this release): IP Lookup with MapLibre + OpenStreetMap and a 5-deep provider cascade (ipapi.co → geojs.io → ipapi.is → ipinfo.io → same-origin PHP proxy as last resort), Ping Check (multi-node via globalping), Traceroute (real server-side hop list per probe), Port Check (TCP reachability via globalping HTTP), HTTP(S) Check (status + DNS / TCP / TLS / TTFB phase breakdown), DNS Lookup (Cloudflare DoH for direct + globalping for multi-resolver compare), MAC / OUI Lookup (full IEEE 39,161-prefix database bundled, offline after first load)
  • Same-origin tools/networking/_api/ip-geo.php proxy as the IP Lookup last-resort fallback - bypasses every CORS / ad-blocker / soft-reload-cache scenario by running the lookup server-side. The "Source" row in the result panel tells you which path answered
  • Code Editor (Monaco) at /tools/code-editor - same engine as VS Code, lazy-loaded from jsdelivr (~3 MB cached after first visit). Six phases of features stacked into one tool:
    • Phase 1 - editor + 80+ languages from monaco.languages.getLanguages() + theme + share-via-URL + copy / download / status bar (cursor / bytes / lines)
    • Phase 2 - Run button for 7 languages: JavaScript (sandboxed iframe), TypeScript (TS compiler then JS), Python (Pyodide CPython 3.12), HTML / CSS (live preview), Markdown (marked.js with GitHub CSS), SQL (sql.js in-memory SQLite). Output panel renders as text, live HTML, or results table depending on runner
    • Phase 3 - multi-tab editor with per-tab Monaco model + IndexedDB auto-save (debounced 400 ms). Tabs survive page refresh / browser close. Drag to reorder, double-click to rename, Cmd/Ctrl+N / W / Tab shortcuts, share-URL imports as new tab without overwriting
    • Phase 4 - Diff mode (Monaco's side-by-side editor, ignore-whitespace toggle, +/- stats), Format button (Prettier 3.2 for JS / TS / CSS / SCSS / LESS / HTML / JSON / MD / YAML, sql-formatter for SQL), 8 extra themes lazy-loaded from monaco-themes (Dracula, Monokai, Nord, Solarized Dark+Light, Tomorrow Night, Cobalt, GitHub)
    • Phase 5 - visible keyboard shortcuts panel on the page, Import file(s) (button + global drag-drop with auto-detected language from extension), Export entire session as JSON, View dropdown menu (word wrap / minimap / whitespace / font +/- / fullscreen), Cmd/Ctrl+P quick fuzzy-find tab switcher overlay
    • Phase 6 - 107 hand-written snippets across 12 languages (JS / TS / Python / Go / Rust / Java / C / C++ / HTML / CSS / SQL / Bash) with VS Code-style ${1:default} tab stops, all 148 CSS3 named colors as suggestions with inline swatches, universal hex-color decorators (drop a #ff5500 in any language and get a clickable color picker - not just CSS / JS / TS), explicit colorDecorators / quickSuggestions / suggestOnTriggerCharacters / acceptSuggestionOnEnter / tabCompletion / inlineSuggest all forced ON
  • Python Obfuscator (Max) at /tools/python-obfuscator - 7-layer client-side obfuscator powered by Pyodide (real CPython 3.12 in WASM). Layers: minify / strip type-hints, identifier rename to 40-64 char confusable X / x / Х / х blobs (Latin + Cyrillic mix, valid PEP 3131 identifiers, all four characters look identical), encrypt strings via chr-chain + base64 with chr-chained module imports (no plaintext "base64" / "b64decode" anywhere), integer mangle to (0X5E906F6 - 0X5E8FF3A)-style big-hex subtraction chains with post-pass tightening, source pack via zlib + base64 + exec (works on any Python 3.x - intentionally not marshal so it isn't locked to one version), multi-layer wrap nests N times, XOR cipher final wrap with random key. Verify button runs both versions in Pyodide and compares stdout
  • JavaScript Obfuscator (Max) at /tools/javascript-obfuscator - wraps the javascript-obfuscator engine (same core as obfuscator.io) and post-processes with Acorn-based AST renaming so every _0xHEX identifier becomes a confusable X / x blob - identifiers in property positions and inside string literals are correctly skipped (the regex version was breaking the engine's RC4 + string-array decoders). Includes UTF-8-safe XOR final wrap that uses unescape(encodeURIComponent(...)) for binary-safe round-trip, plus String.fromCharCode-built names so eval / atob / globalThis / decodeURIComponent / escape never appear as grep-able strings. Engine options dialled to safe defaults to keep the output runnable
  • Paste-to-router rebuild - the global Cmd+V interceptor was unreliable; replaced with a bottom-right FAB (mirror of the workbench's bottom-left). Drag any file / image / text / URL onto the FAB or anywhere on the page and a panel opens with format-aware suggestions. New: drop a PNG and you get "All PNG converters (folder)" + direct PNG → WebP / JPG / AVIF / GIF / ICO links instead of one generic "All converters" link. The converter index page (tools/images/converters) now reads #from=png from the URL hash and pre-selects that filter chip on load
  • Drop-handoff into target tools - drops are stashed (text in sessionStorage, files in IndexedDB) for 10 minutes; suggestion links carry ?paste=1; on the target tool page the paste-router auto-prefills any <input | textarea data-paste-accept> or <input type="file" data-paste-accept> via DataTransfer + change event. File Inspector + universal converter + per-format converters all wired with data-paste-accept via the porter / templates
  • Auto-open paste panel when a file is dragged over the page - bottom-right panel slides in immediately so users see a drop target without having to find the FAB. Auto-closes after a short window if nothing is dropped. Tool-specific drop zones still receive their native drop events (we only preventDefault inside our own panel + FAB)
  • 17-shortcut keyboard reference panel rendered visibly on the Code Editor page (in the content area, not buried in FAQs) - styled <kbd> grid covering every keybinding from Cmd/Ctrl+S download to Cmd/Ctrl+Shift+↑/↓ move-line
  • IP Lookup hardening - dropped ipwho.is entirely (their free tier started returning {"success":false,"message":"CORS is not supported"} for browser calls), reordered to ipapi.co primary then geojs.io / ipapi.is / ipinfo.io / proxy. Each provider now wrapped in a 5 s AbortController timeout and given a per-request cache-buster (?_ub=<ts><rand>) so soft-reload never serves a sticky CDN-cached 403
  • Tool-script auto-loader (tool.php) now passes {slug}.js through ub_asset() for filemtime cache-busting, and sw.js explicitly skips caching /assets/(js|css)/tools/ - tool JS is always fresh from the network. Was serving stale ip-lookup.js for some users; now impossible
  • Code editor IntelliSense now actually works - root cause was an undefined esc() helper crashing renderTabs() on first render before the editor model was attached. Compounding issues found and fixed in the same pass: data-URL Monaco worker shim is blocked by stricter CSP in modern Chrome (switched to Blob-URL), and the worker's baseUrl was incorrectly ending in /vs (now stripped, language workers resolve correctly). CSS color completion provider was also flooding the popup at selector position - now scoped to value position (after :)
  • Paste-router suggestion URLs - every /tools/<category>/<slug> link was 404ing because the site only routes /tools/<slug> (.htaccess doesn't have category-folder rewrites except for /tools/images/*). Stripped the category segment from every suggestion in paste-router.js; image URLs intact since they have specific rewrites
  • JavaScript obfuscator XOR wrap was treating UTF-8 bytes as UTF-16 code units, garbling the moment confusable characters appeared in the source. Now uses unescape(encodeURIComponent(...)) on encode + decodeURIComponent(escape(...)) on decode for binary-safe round-trip. Python obfuscator's marshal-based pack switched to source pack so output runs on any Python 3.x instead of being version-locked to Pyodide's 3.12
  • File Inspector tab row, hash row, KPIs, badges, hex view, dropzone, alerts, bookmarks, kbd elements, struct overlays - every component restyled to match v3 design tokens. v2.1 brand red #f93a13 / rgba(249,58,19,…) swept site-wide; font-weight 950 / 900 dialled down to 700 / 600 for v3's DM Sans. Threat detection (tab + 1,337-line engine + MITRE ATT&CK references) removed entirely
  • Threat Scan tab from File Inspector + the ub-threat-engine.v2.0.js library. Removed from $toolMeta, removed from formula cards, removed from "How to use" docs, removed from keyboard shortcuts. Inspector JS dropped 85 KB. UB.threat calls in the inspector core were already feature-checked so dropping the engine cleanly disables the feature with no breakage
  • ipwho.is from the IP Lookup cascade (broken for free-tier browser callers as of April 2026)
v3.1.4

V3-Native File Inspector v5 — 22 Tabs, 56 Parsers, 800+ File Types

The file inspector at /tools/file-inspector was a 55-line stub since the v3 migration — dropzone with no analysis behind it. Brought back the v2.1 File Inspector v5.0 natively in v3: 22 analysis tabs, 56 format parsers, interactive hex editor with inline editing and undo / redo, steganography detection, file carving with embedded-file extraction, 9 binary visualisations (byte frequency, entropy heatmap, Hilbert curve, digram plot, sliding-entropy window, pixel map, LSB bit planes, image histogram, structure treemap), PE / ELF / Mach-O header parsing, 800+ file-type identification via UB.fileTypes, string extraction with URL / email / IP / path classification, side-by-side two-file comparison, and export to JSON / hex dump / C-array.

Not a direct port — re-skinned against v3's own design tokens. Every var(--ub-*) reference in v2.1's CSS and inline HTML styles is rewritten to v3 equivalents (--border, --bg-card, --text-primary, --accent, --radius-*, --font-mono, --shadow-sm); a :root compat bridge aliases anything still referenced by the globally-loaded ub-toolkit.css so .ub-card / .ub-btn / .ub-alert resolve against v3's theme instead of the v2.1 .ub-theme-* classes that v3 doesn't use. Every .ub-btn inside the tool was also explicitly overridden to a v3-native pill (v2.1's red-gradient ::after pseudo-element killed) so the Copy / Share / Download / Export row matches the rest of v3.

Threat Scan tab removed — too much surface area for a client-side pretend-AV. The inspector's JS already feature-checks if (window.UB && UB.threat) around every call site, so dropping the 1,337-line threat engine is enough to disable the feature cleanly without touching the inspector core. HTML scrubber strips the tab button, the whole panel, its documentation <details> block, and the Y keyboard shortcut.

  • File Inspector tool fully operational — drop a file and get hex view with clickable bytes + range selection, identity panel (magic bytes + MIME + extension mismatch warning), hash panel (SHA-256 / SHA-1 / SHA-512 / CRC-32 / MD5), strings panel, format-specific parsers, PE / ELF analysis, entropy visualisations, steganography checks, carving, and side-by-side comparison
  • Shared engines at stable public paths — /assets/js/ub-file-engine.v2.0.js (1,509 lines, UB.file.detect / parsers / inspectBytes / scanEmbedded / fromExtension / detectMismatch) and /assets/js/ub-file-types.v1.0.js (1,607-entry extensions database populating UB.fileTypes). Emitted as deferred <script> tags from renderToolInterface() so they load before tool.php's auto-loaded assets/js/tools/file-inspector.js
  • Auto-load pattern for tool-specific CSS — header.php now mirrors tool.php's existing JS auto-load: if assets/css/tools/{slug}.css exists, it's included on that tool's page. No template edits required to add tool-specific styles
  • tools/_dev/port-file-inspector.py — one-shot reproducible porter. Reads v2.1/modules/files/file-inspector.php, rewrites every v2.1 token to its v3 equivalent (or a literal for font-size / gap / hit-target / focus glow), strips v2.1-path <script> tags from the HTML, wraps the output in a .fi-root breakout that spans v3's 2-col .ub-tool-layout grid, scrubs all threat-related DOM (tab + panel + details + keyboard hint), and emits the final v3 PHP shell with UB-CERT $toolMeta
  • V3-native .ub-btn override scoped to .fi-root — kills the v2.1 gradient ::after pseudo-element, applies --border / --bg-card / --accent colouring, adds hover / active / disabled / primary / secondary / block variants, matches the weight and radius of v3's other buttons
  • Stub at tools/media-files/file-inspector.php (55 lines, no JS, placeholder dropzone) replaced with the full ported tool. $toolMeta now has a richer description, seven-tag set, four use-cases, and five related tools
  • Threat Scan tab, 46-engine malware scorer, 70+ AV-vendor simulation, MITRE ATT&CK kill-chain mapping, and the 1,337-line ub-threat-engine.v2.0.js library. Inspector JS dropped 85 KB as a result
v3.1.3

Constellation Cinema, Paste-to-Router, Workbench & Ambient Night Sky

Three novel features most utility sites don't have, plus a complete rewrite of the homepage hero as a 16-page scrollable constellation. The hero now renders each category as its own night-sky with trending-aware star sizes; paste anything anywhere on the site and a panel suggests the right tools for it; pin your favourite tools to a persistent shareable workbench; and when you walk away from the tab, shooting stars start drifting across the background.

  • Horizontal Constellation Cinema hero — 16 scroll-snap pages, one per category, each rendering its tools as a lazy-loaded SVG constellation. Pages render on first intersection (plus one neighbour pre-render) so opening the site doesn't pay for all 1,536 stars up-front. Prev / next arrow buttons, keyboard arrow-key nav, pagination dots at the bottom, per-category hue + halo
  • Stars feel like a real night sky, not a perfect spiral — each star's position is perturbed with deterministic hash-seeded noise (radial ±22%, angular ±0.38 rad), and sizes / opacities vary per star via natural "magnitude" variance. Trending tools (from MostUsed localStorage) grow larger with a subtle 3.6 s twinkle; dense categories scale sizes down to avoid clutter. Tooltips show usage counts on hover
  • Paste-to-router (assets/js/paste-router.js) — global Cmd/Ctrl+V listener sniffs clipboard contents across 14 types (images, URL, JWT, JSON, hex color, UUID, unix timestamp, base64, CSV, email, IPv4, hex string, regex, markdown, plain text) and floats a panel suggesting the actual tools that accept each type. Preserves normal paste behaviour when an input is focused. Stashes the paste in sessionStorage.ub_paste_payload so individual tool pages can opt-in to prefill from it later
  • Workbench (assets/js/workbench.js) — persistent pegboard of pinned tools. Pin button added to every tool-page header; a bottom-left dock FAB with pin-count badge opens a slide-in drawer listing every pin. "Copy share link" base64-encodes the set into a #wb=… URL that any browser can import (with a toast confirm). Max 12 pins, gated on personalization consent. Exposes window.UB.Workbench.{add,remove,has,getItems,open} for tool pages to call directly
  • Ambient reactive background (assets/js/ambient.js) — a full-viewport canvas behind all content with ~90 theme-aware drifting, twinkling stars. Idle-aware: 0–3 min drift-only, 3–5 min one shooting star every 45–90 s, 5–10 min every 20–40 s, 10+ min every 10–25 s with ~22% chance of 2–3 star bursts. Auto-pauses on hidden tab and fully disabled under prefers-reduced-motion. DPR-aware, costs under 1% of a frame with 90 stars + trails
  • Homepage hero replaced entirely — the old single-view hero is gone. All 16 categories are now reachable from the cinema pagination dots in addition to the header dropdown, so the homepage doubles as category discovery
  • Tool-card star visuals now use variable r and per-star opacity from SVG attributes instead of a fixed CSS r:5 hover override — lets big trending stars stay big on hover. Hover / focus state now adds a coloured stroke ring instead of resizing the circle
  • Body now has isolation:isolate so the ambient canvas at z-index:-1 stays above the body background but below all content, without needing to touch z-index on every sibling
  • Corrected the old hero JS controller (CinemaRail) which didn't support horizontal scrolling or lazy rendering — replaced with a new Cinema controller that tracks scroll position via IntersectionObserver rooted on the track, freeing each page's JSON data blob after its stars are in the DOM to reclaim memory
v3.1.2

Lighthouse 100s — Perf Pass, Critical-CSS Split, Service Worker & Bug-Fix Sweep

Pushed every Lighthouse category to 100 (Performance, Accessibility, Best Practices) with a coordinated performance pass: critical CSS inlined, search index deferred, long-lived immutable caching, and a service worker for repeat-visit speed. Plus the ugly stuff — a $slug variable collision that silently broke the Media & Files featured banner, a typo in .htaccess routing the universal converter to a file that didn't exist, and a header layout that drifted left on wide screens.

  • Critical CSS extractor (tools/_dev/build-critical-css.py) — pulls above-the-fold rules from style.css into assets/css/critical.css. Header inlines the contents in a <style> block and defers the rest via rel="preload" + onload swap, so first paint doesn't wait on the main stylesheet
  • Service worker (sw.js) — cache-first for static assets (CSS / JS / fonts / images) with automatic cache-version bumps per release; network-first for HTML; offline fallback to the homepage shell. Registered during requestIdleCallback so it stays off the critical path
  • Cache-busting helper ub_asset() in config.php — every stylesheet and script URL is now appended with ?v=<filemtime>, so a 1-year immutable cache never serves stale bytes after an edit
  • Aggressive Cache-Control headers in .htaccesspublic, max-age=31536000, immutable for every CSS / JS / WOFF2 / image / icon; month-long cache for JSON / webmanifest; no-cache, must-revalidate for HTML. Fallback MIME types added for WOFF2, WOFF, webmanifest, ICO in case Apache ships without them
  • Non-blocking font loading — core fonts now preloaded with as="font" and self-hosted when the WOFF2 files are present (see v3.1.1); Google Fonts kept as a canary-gated fallback
  • Mid-viewport CSS-compactor script (tools/_dev/compact-css.py) — second pass tightened property formatting so no stray whitespace remains after ; or around : in leaf rule bodies, while preserving spaces inside values like margin:0 0 10px or calc(100% - 10px)
  • Per-tool hand-drawn OG card infrastructure — tool.php checks for /img/og/{slug}.png (or .jpg) and wires it to og:image / twitter:image, falling back to /img/og-default.png when a slug doesn't have a custom card yet
  • Featured "Image Converters" banner now also renders on /category/image-converters in addition to /category/media-files, with a single consistent copy pointing at the 737-converter index
  • Search index (search-index.json, ~472 KB) no longer fetched on page load — deferred until the user focuses a search box or requestIdleCallback fires. Removes the biggest Total-Blocking-Time contributor on cold loads
  • MostUsed.render() and CategoryFilter.init() moved to requestIdleCallback so they don't contend with first paint or Time-to-Interactive
  • Color tokens bumped to WCAG AA-clean values — --text-tertiary went from #6b727d (3.8:1, failed) to #a0a6af (6.1:1, AA) on dark; similar bump on light. --text-secondary also lifted to AAA-grade (8.3:1) on both themes. Fixes every contrast issue Lighthouse flagged across panel labels, tool-card categories, hero badges, filter labels, and footer text
  • Header layout — .ub-header__actions now has margin-left:auto so the Logo / Search / Actions row fills the full 1240 px content width on wide screens instead of all three bunching against the left
  • $slug variable collision that silently broke in_array($slug, ['media-files', 'image-converters']) on category pages — the theme-panel's font-picker foreach loop used $slug as its iterator, clobbering the page-level variable with the last font key ('georgia'). Renamed loop vars to $__ub_font_slug / $__ub_font_def to prevent future include-scope pollution
  • Universal image converter 404 — .htaccess rewrite pointed /tools/images/convert-image at universal-converter.php (never existed); corrected to the actual file convert-image.php
  • PWA manifest 404 — manifest.json referenced /img/icon-192.png and /img/icon-512.png which weren't present. Swapped to the existing SVG favicon with "sizes":"any" (valid PWA icon format since 2020) and switched all paths to relative so the manifest works at both /ubv3/ (local) and / (prod)
  • Four config-registered tool slugs (break-even, currency-converter, loan-amortization, sales-tax) had no backing tool file and were falling through to tool.php's auto-generated "Coming Soon" placeholder. Each now 301-redirects to its canonical counterpart
  • Sitemap-accurate <lastmod> — uses real filemtime() per tool file instead of always emitting today's date. Pure-redirect aliases are now excluded so crawl budget isn't wasted on 301-only URLs
  • Deferred consent.css via rel="preload" + onload swap — shaves another ~1.4 KB gz off the render-blocking critical path since the cookie banner is always below-fold
  • Category dead-code re-merge — an ambitious category.css split briefly pulled .ub-featured-banner / .ub-filter-* rules out of style.css, but those classes are also used on index.php and tools/images/converters.php. Rules moved back into style.css and the file was deleted
  • Homepage horizontal-scroll category bar (replaced in v3.1.1 by the dropdown, confirmed gone)
  • Experimental og-card.php auto-generator and assets/og-cache/ — user preference shifted to hand-drawn cards
v3.1.1

Final Migration, Lazy Assets, Font Picker & SEO Pass

Closed out the v3 migration and turned attention to the page itself — how fast it paints, how it looks on social, and how much control users have over typography. Site is now 100 % native UB-CERT (zero legacy templates remaining), fonts are user-selectable, and critical-path JS/CSS dropped by ~45 KB per page.

  • Numbers & Math — final 41 legacy-template tools ported to UB-CERT (rounding, bandwidth, big-number, binary, bra-size, capstan-winch, complex-numbers, confidence-interval, convolution, day-of-week, dew-point, dice-roller, exponential-growth, GDP, golf-handicap, half-life, heat-index, height, hex, hours, IP-subnet, long-division, love, mass, matrix, molarity, number-sequence, p-value, password-generator, permutation & combination, probability, remainder, resistor, sample-size, shoe-size, sleep, time-card, time-duration, voltage-drop, weight, wind-chill, z-score)
  • Finance — all 77 tools now native UB-CERT: 50 canonicals built from scratch (mortgage, loan, amortization, compound & simple interest, investment, retirement, 401(k), IRA, annuity, bond, CD, budget, tip, discount, VAT, sales tax, salary, take-home paycheck, income tax, estate tax, debt payoff, credit card, DTI, margin, ROI, IRR, NPV / present / future value, payback period, inflation, rental property, depreciation, refinance, commission, currency, lease, auto/business/FHA/VA/UK/Canadian mortgage variants, etc.) plus 27 redirects that collapse near-duplicate tools into their canonical equivalents
  • Font picker in the Appearance panel — pick from a curated list (Default / System UI / Inter / Atkinson Hyperlegible / Lexend / Georgia out of the box). Registry lives at config/fonts.php — drop a WOFF2 in assets/fonts/ and add one array entry to expose a new option. Non-default fonts are lazy-loaded on pick so adding more costs nothing until someone selects one. Monospace outputs stay on JetBrains Mono regardless.
  • Self-hostable core fonts — DM Sans & JetBrains Mono. Drop the WOFF2 files in assets/fonts/ and the header automatically swaps Google Fonts for local delivery (PHP canary check on every request). Eliminates two third-party TCP handshakes on cold first paint when enabled.
  • Category navigation dropdown — replaces the horizontal scrolling category bar with a responsive grid dropdown (4 cols desktop, 2 cols tablet, 1 col phone). All 16 categories visible in one panel; the trigger button shows the current category on tool and category pages. Works identically on desktop and mobile — no more hidden overflow.
  • Image converter template now renders inside the v3 shell — rewrote tools/images/convert-image-template.php to set $toolMeta + define renderToolInterface() / renderToolContent() instead of emitting its own <!DOCTYPE>. Shared assets/js/tools/image-converter.js drives drag-drop, quality/background options, and download for all 737 per-format converters.
  • OG image + enhanced Twitter card infrastructure — og:image, og:image:width, og:image:height, og:image:alt, twitter:image, twitter:title, twitter:description now emitted site-wide. Drop a 1200×630 PNG at img/og-default.png and every page gets a social preview card. Per-page override via $ogImage.
  • Persistent migration-status tracker — v3-migration-status.tsv records the native / redirect / other status of every tool so future audits are one command away
  • Google Fonts stylesheet now loads non-blocking via rel="preload" + onload swap with a <noscript> fallback — saves roughly 150–300 ms of LCP on cold pageviews
  • Easter eggs split into a tiny detector loader (~4 KB) and the full engine (~37 KB JS + ~12 KB CSS). The engine only loads when a user actually fires a trigger — the 95 % of visits that never type "matrix" into the search bar no longer pay the 45 KB cost. API preserved via window.UB_EE.fire() / .bunker() / .bees().
  • Cookie-consent stylesheet deferred via rel="preload" — shaves another ~1.4 KB gz off the critical path since the banner is always below-fold
  • Sitemap now emits real filemtime() values for <lastmod>, skips pure-redirect aliases (they're not canonical pages), and dedupes by slug across categories — Google gets truthful crawl signals instead of "every URL changed today"
  • Sitemap image-converter URLs now share a single <lastmod> derived from the shared template's mtime
  • Twitter card upgraded from summary to summary_large_image with explicit twitter:title / twitter:description
  • /tools/images/convert-image returned 404 — the .htaccess rewrite pointed at universal-converter.php (doesn't exist); corrected to convert-image.php
  • Four config-registered slugs had no backing tool file and fell through to the auto-generated "Coming Soon" placeholder in tool.phpbreak-even, currency-converter, loan-amortization, sales-tax now 301 to their canonical equivalents so no indexed URL lands on a stub
  • Changelog's dateModified schema now updates with each release
  • Horizontal category scrollbar in the header (replaced by the dropdown above)
  • Hamburger mobile-menu toggle — the dropdown is responsive on its own so the dedicated mobile trigger is no longer needed
  • Eager easter-eggs.css link in the header — now injected by the loader only when a trigger fires
v3.1.0

Native-First Migration & Category Cleanup

Replaced the v2.1 iframe shim with native tool implementations across every category. Tools now render directly in the v3 shell with UB-CERT layout, shared CSS components, and per-tool metadata — no embedded legacy pages, no frame chrome anywhere. Also split, deduplicated, and re-routed the tool index to reflect the cleaner structure.

  • Numbers & Math — 13 iframe tools ported to native (base converter, binary/ASCII/hex/Base64, Braille, file size, Intel HEX, Morse, temperature, text case, time formats, unit converters, Roman numerals) plus 3 new tools built from 404s (number formatter, random number, scientific notation)
  • Color & Design — all 13 iframe tools ported: color picker, contrast checker, CSS color converter, CSS color names, safe web colors, CSS variables generator, gradient generator, palette generator, palette-from-image, pattern generator, pick-from-image, color blindness simulator
  • Automotive — HP & Torque Lab, OBD-II code lookup, and VIN decoder rebuilt natively
  • Text & Encoding — MD5 hash generator (embedded MD5 implementation) and fake-name generator rebuilt natively
  • Reference category — all 202 reference tables ported to native (100%), covering: ASCII, resistor color codes, AWG ampacity, HTTP methods, MIME types, DNS records, SSL/TLS versions, file extensions, physics constants, number systems, USB / Bluetooth / WiFi, SQL data types, Linux shell commands, periodic table, geometry formulas, trig / triangle / matrix / Fourier, Earth constants, Ohm's law, password strength, cryptographic / file hashes, programming shortcuts / syntax, water properties, planetary data / gravity / atmospheres, full AI stack (model sizes / token costs / quantization / eval / types / dataset formats / embedding models + eval + uses / activation functions / loss functions / gradient descent / system design), battery basics / charging / discharge / Peukert / self-discharge / charging-voltage, BJT / MOSFET vs IGBT / transistor pinouts, bolt torque / fastener materials / thread sizes, capacitor types / charge time, LED basics / resistor table, decibel / SNR / harmonics, EM spectrum / optics / optical lenses, FFT / Fourier / quantization, file size / storage / memory hierarchy, CPU vs GPU / architecture / ports, filesystem / network cable / optical fiber / wireless protocols, connectors / pinouts / electronics packages / PCB design / trace width / materials / layer stackups, escape velocity / atmosphere layers / chemical elements / fuels / combustion / solar irradiance, electrical safety symbols / IP codes / environmental standards, EMI / flicker / distortion / clock tolerances, wire gauge / voltage drop, fuse types / short-circuit / timing basics, RC / LC resonance / reactance / filters / biquad / filter Q / return-loss-VSWR / RF connectors / RF attenuation, antennas (basics / types / radiation patterns), PWM basics / duty cycle, power factor / formulas / converters / loss / supply efficiency / noise filtering / standards / UPS, 3-phase / transformers, relays / switches / servo-stepper / motor drivers / coil-inductance / inductor cores, thermal (conductivity / expansion / resistance / cheat / derating / interfaces), thermistors, signal integrity, material / spring / magnetic / dimensionless properties, statistical (distributions / tests / correlation), fluid dynamics / gas laws / humidity, JSON schema / JSON vs XML / internet protocol history / data transfer / floating-point / error propagation, mechanical leverage / moment of inertia / units / measurement tolerances, phone star codes, eddy-current losses, load factor, density, speed-of-light, thermodynamics laws
  • Shared reference renderer — single _render.php helper powers all native reference pages (searchable tables, KV lists, notes, custom HTML) — future ports are data-only
  • Image Converters — split out of Media & Files into their own top-level category (737 convert-image-X-to-Y tools)
  • Media & Files pruned from 839 links to ~100 — image converters moved to dedicated category; universal converter redirects to the new landing page
  • Reference tool template — read-only tables render in the same UB-CERT shell as interactive tools, with consistent search, breadcrumbs, and related-tool sidebars
  • Slug router bug — hardcoded 737-converter injection in category.php that pulled image converters into Media & Files at render time
  • All known 404s in Numbers & Math now resolve to working pages
  • Duplicate slugs normalized with 301 redirects: number-base → base-converter, formats-converter → binary-ascii-hex-base64, roman-numeral → roman, unit-converter → unit-converters, css-color-parser → css-color-converter, wire-gauge-reference → wire-gauge-table, fuse-reference → fuse-types-and-ratings, pwm-cheat-sheet → pwm-basics, snr-cheat-sheet → signal-to-noise-ratio, three-phase-power → three-phase-basics, thermal-resistance-calculator → thermal-resistance, swr-cheat-sheet → return-loss-vswr, signal-integrity → signal-integrity-basics, rc-cheat-sheet → rc-filters, switching-regulator-efficiency → power-supply-efficiency, pcb-trace-cheat-sheet → pcb-trace-width-guide, water-density-temperature → water-properties, derating-reference / power-derating-with-temp → thermal-derating-curves
  • Dead config entries and base-file stubs: auto-tool-base, converter-index-backup, stale convert-image in Media & Files
  • v2.1 iframe shell from every ported tool — pages now render fully in the v3 layout with no embedded frames
v3.0.0

V3 — Complete Platform Rebuild

Utilities Bunker V3 is a ground-up rebuild. The platform has been restructured from a collection of standalone tool pages into a connected, scalable, privacy-first tool ecosystem.

  • New category system — 12 topic-based user-facing categories replacing the old function-based navigation
  • Tool metadata system — every tool now includes structured metadata for search, related tools, and AI recommendations
  • Theme and accessibility engine — dark/light/system modes, custom accent/background/header/card colors, color-blind presets (protanopia, deuteranopia, tritanopia), high contrast mode, and readability controls (font size, line height, letter spacing)
  • Client-side search with instant results, partial matching, synonym support, and keyboard navigation
  • "Most Used on This Device" — homepage section powered by localStorage usage tracking
  • UB-CERT tool layout — standardized split-panel interface with tool inputs on the left and visualization/results on the right
  • Show Work section on calculator tools — transparent step-by-step breakdowns
  • SVG circuit visualization for electronics tools with real-time value updates and animated current flow
  • Per-tool content standard — required sections (title, description, how to use, interface, results, last updated) with conditional and optional sections (formulas, FAQ, use cases, history, visualization)
  • Schema.org implementation — SoftwareApplication, CollectionPage, ItemList, BreadcrumbList, FAQPage per page type
  • Sticky related tools sidebar on tool pages
  • Single-config deployment system — one file controls local/production switching
  • Functional classification system — internal tool typing (Calculator, Converter, Generator, Analyzer, Formatter, Viewer, Tester, Estimator, Reference) for filtering and search
  • Category page filtering by functional type
  • Privacy policy, About page, and Changelog
  • Complete UI redesign — card-based layout, DM Sans + JetBrains Mono typography, utilitarian dark-first aesthetic
  • Restructured file system — assets consolidated into /assets/css, /assets/js, /assets/includes
  • Responsive design rebuilt for mobile-first with breakpoints at 960px, 800px, 700px, 500px, and 440px
  • AMP support — removed in favor of custom performance-first architecture
  • Domain-based secondary categories — replaced by internal metadata tags
v2.x

Version 2 — Tool Website Era

V2 was the first public version of Utilities Bunker. It operated as a straightforward tool website with individually built pages. While functional, it lacked the architecture needed for long-term scaling.

  • Initial tool collection across electronics, web dev, and math categories
  • Basic dark mode support
  • Mobile-responsive layouts
  • Multiple UI iterations and design updates
v1.0

Version 1 — The Beginning

The original Utilities Bunker. A handful of tools built for personal use that grew into something worth sharing. Simple HTML pages with inline JavaScript. No framework, no system, no pretense — just tools.

  • First tools: Ohm's Law Calculator, Base64 Encoder, JSON Formatter
  • Basic UI with minimal styling