Vitrine v1.35.0
Fixed
- The packaged app's image workers never worked — every heavy pass ran on the UI thread. Cause (two stacked): Vite never bundled the worker (the
new URL()/new Worker()split across two modules defeated its static detection, so the installed app shipped raw TypeScript as the worker file — dev-mode transpilation masked it, meaning the v1.29.0 "worker revival" only ever worked in dev), and Chromium blocks ALLfile://worker scripts anyway. Fix: the worker is now a compiled chunk booted from ablob:URL in the packaged app (dev unchanged), with contract tests pinning the whole arrangement. Verified live: pool init 189 ms, a ≥1MP pass through a real worker in 62 ms. Affects:src/workers/createPipelineWorker.ts(new),vite.config.ts,src/services/WebWorkerImageProcessor.ts. - Batch export was pathologically slow (75 JPEGs ≈ 1h30, ~72 s/photo). Causes: a stale "workers may differ" safety flag forced every export onto the single UI thread (workers were dead anyway — see above); the sharpen chain's Richardson-Lucy deconvolution paid per-pixel boundary clamps in its hottest loop; photos were decoded, processed, and encoded strictly one at a time. Fixes: exports route through the worker pool (with proof: outputs SHA256-identical to the old path), the blur inner loop is 3× faster bit-identically, and the batch pipelines decode-ahead and encode overlap. Measured live: 34.7 s → 18.1 s/photo on 20MP JPEGs with sharpening (steady-state ~16 s). Guardrails kept: noise-reduction exports stay on the main thread (their GPU path lives there), small exports (≤4096 px) keep their GPU passes, and the exposure stage still clamps after a vignetting correction. Affects:
src/services/MultiExportService.ts,src/services/exportRouting.ts(new),src/utils/enhanceOps.ts,src/utils/enhanceRestore.ts,src/services/ImageProcessingPipeline.ts,src/components/Dialogs/ExportDialog.tsx. - Motion deblur could bake corrupted regions into the photo and froze the UI. Causes: the NAFNet model deterministically garbles some bright/high-contrast windows (outputs at ±28 where valid data is 0–1) and nothing checked; independent 768 px windows with a 40 px feather disagree across long motion streaks (ghost seams); the finishing pass ran the whole frame on the UI thread; and the develop pass cached ~320 MB per module for nothing. Fixes: every tile output is sanity-checked (a garbled window keeps its original pixels and you're told how many were skipped), DirectML runs 1536 px windows with a 128 px feather, the finishing pass runs in the revived enhance worker (UI stays responsive), and bake develop passes no longer populate caches. Affects:
electron/aiDeblur.cjs,src/services/EnhanceService.ts,src/utils/createEnhanceWorker.ts(new),src/services/EnhanceWorkerClient.ts. - Switching photos during an Enhance/AI bake could write the previous photo's pixels, revert point, and saved edits onto the new photo. Cause: no identity re-check after the minutes-long develop + inference awaits, while the filmstrip stays clickable. Every bake now captures the target photo's identity up front and cleanly cancels (with a notice) if you've moved on; every bake result is also size- and sanity-validated before it may replace the working base — the v1.32.0 corruption class is now guarded at its highest-consequence write. A crashed or hung enhance worker now rejects cleanly (watchdog) instead of leaving the panel stuck busy. Affects:
src/services/EnhanceService.ts,src/services/EnhanceWorkerClient.ts,src/services/EditPersistenceService.ts. - AI upscale on a machine without GPU acceleration silently ran on the CPU — a 20MP ×2 upscale meant ~2,000 tiles and over an hour, uncancellable. The AI route is now available only when the model actually runs on DirectML; otherwise the deterministic (Lanczos) upscaler serves the same request at the same scale. Affects:
electron/aiUpscaler.cjs,src/services/EnhanceService.ts.
SHA256 checksums
81ed070f2acf24203e7d2b69948f5a7e3f1335ded4694bb1501e224431aa1b23 Vitrine Setup 1.35.0.exe
3d81ec05eb208f740602cbba668eca3d75493ba66f63b31645a6d99bdd0d932c Vitrine 1.35.0 portable.exe
Verify on Windows: CertUtil -hashfile "<downloaded file>" SHA256