A lightweight, fully offline PDF tool for personal use. Built because I hate using Adobe tools and wanted something snappier and lightweight. All PDF processing happens locally in the app; files never leave your machine.
- Open & view — open PDFs (button or drag-drop), every page as a crisp thumbnail, click any page for a large viewer with an Enhance contrast toggle for faint scans; scroll or pinch to zoom (drag to pan)
- Page management — drag-to-reorder (single page or a whole multi-select block), rotate, delete, insert blank or duplicate pages; box-select with a marquee, or click + Ctrl-click; a thumbnail-size slider
- Page groups — tag pages with color groups (an organizing aid that never changes the saved file): select, rename, gather, or move a group as a block, and export each group as its own PDF
- Merge / Split / Extract / Compress — combine multiple PDFs (open or drag several), extract selected pages to a new PDF, split into a folder of files, or compress (re-encode pages) to shrink scans
- Find — Ctrl+F to search text across all pages with on-page highlights (works on text PDFs and on OCR'd scans)
- OCR — recognize text in scans (offline, bundled Tesseract) and save a copy with an invisible, selectable/searchable text layer
- Markup & annotation — highlight / underline / strikethrough, freehand pen, lines / arrows / boxes, and colour sticky-note comments; all baked into the saved PDF
- Text & forms — stamp text anywhere + auto-detect & fill real AcroForm fields (text, checkbox, radio, dropdown), flattened on save
- Signatures — draw (with a trackpad glide mode) / upload / reusable saved library; place, drag, resize; baked in on save
- Images — insert PNG/JPG as pages; export selected pages as PNG (2×, overlays baked in)
- Polish — save-in-place (Ctrl+S overwrites the open file) + recent-files list, automatic updates from GitHub Releases,
.pdffile association (double-click to open, single-instance), keyboard shortcuts (Ctrl+O/S, Ctrl+A, Delete, Esc), remembered window size, custom icon, logo-matched theme
| Layer | Choice | Role |
|---|---|---|
| Shell | Tauri 2 (Rust) | Tiny native window, dialogs, file I/O |
| UI | React + Vite + TypeScript | App interface |
| Render | pdf.js (pdfjs-dist v6) |
Page previews / thumbnails |
| Edit | pdf-lib | Merge, split, reorder, stamp, forms |
| Reorder | @dnd-kit | Drag-and-drop page grid (M2) |
| Signatures | signature_pad | Draw signatures (M5) |
- All editing runs in the webview (JavaScript). Rust only provides the native
shell:
read_file/write_filecommands (efficient binary transfer) and the native open/save dialogs viatauri-plugin-dialog. - pdf.js renders with a top-left origin (CSS px); pdf-lib writes with a bottom-left origin (PDF points). The coordinate transform between them is the key detail for text-stamping and signature placement (M4/M5).
- Native OS file-drop is disabled (
dragDropEnabled: false) so HTML5 drag-and-drop works inside the webview. - pdf.js v6 decodes JBIG2/JPEG2000 scans via WASM that it doesn't auto-locate —
those assets are copied from
node_modules/pdfjs-distintopublic/pdfjs/and pointed at viawasmUrl/iccUrl/standardFontDataUrlinsrc/lib/pdfjs.ts. (Re-copy them after upgradingpdfjs-dist.) - Stamp/signature placement is converted to PDF coordinates with pdf.js's
viewport.convertToPdfPoint, so it stays correct on pages with a/Rotate. - The app icon is generated from
src-tauri/app-icon.svgvianpm run tauri icon.
npm install
npm run tauri dev # compile Rust + launch the desktop app (first run is slow)
npm run build # type-check + build the frontend only
npm run tauri build # produce a distributable installerRequires Node.js and the Rust toolchain


