TreeMap
무료 오픈소스 디스크 사용량 시각화 도구로, 사각형 트리맵·중복 파일 탐색·디스크 가득 예측·정리 시 파일을 휴지통으로만 이동한다
키를 누른 채 말하고 놓으면 된다
Hold a key, talk, and let go — clean, ready-to-send text appears wherever you type. Free, private and open source voice typing for Windows. Works offline, no account needed.
생산성Rust · TypeScriptGitHub @adityashelke04온라인운영자 미확인
써 보셨어요? 한 번만 눌러 주세요. 로그인은 필요 없어요.
Local-first push-to-talk dictation for Windows. Hold a key, speak, release — correctly formatted text appears at your cursor, in any app. No cloud, no account, no telemetry.
저장소 README에서 가져옴
README 전체를 불러오는 중입니다. 아래는 저장된 발췌입니다.
Local-first voice dictation.
Hold a key, speak, release — correctly formatted text appears at your cursor, in any app.
No cloud, no account, no telemetry.
⬇ Download for Windows — one .exe, speech engine included.
All releases → · Docs · Changelog
Status. It runs end to end on Windows 10 and 11 — hotkey, capture,
transcription, formatting, injection and history — and every release is
published on the releases page.
Two things are not done: nothing is code-signed, so Windows will warn you about
an unknown publisher, and the bundled speech engine is CPU-only.README 전문 보기 ↗Local-first voice dictation. Hold a key, speak, release — correctly formatted text appears at your cursor, in any app. No cloud, no account, no telemetry.
openvoice-dictation.vercel.app
⬇ Download for Windows — one .exe, speech engine included.
All releases → · Docs · Changelog
Status. It runs end to end on Windows 10 and 11 — hotkey, capture, transcription, formatting, injection and history — and every release is published on the releases page. Two things are not done: nothing is code-signed, so Windows will warn you about an unknown publisher, and the bundled speech engine is CPU-only.
Most people speak around 150 words a minute and type around 40. That gap is the entire reason dictation exists, and the reason almost nobody uses it is that raw transcription is not writing. It gives you your filler words, no punctuation you did not say out loud, and no idea which app you were talking into.
Whisper transcribes beautifully and formats nothing. Ask it to transcribe someone
writing code and you get use effect for useEffect, cube control for
kubectl, the literal words "open parenthesis", and Git status. — capitalized,
punctuated, and unrunnable.
Those aren't model bugs. They're accurate transcriptions of what you actually said. Fixing them is a text-processing problem, and text processing is deterministic, testable, and improvable one rule at a time.
So OpenVoice treats the speech model as a swappable commodity and puts all its effort into what happens next. That's the whole bet.
you say: "um so we need to call use effect here comma then return null"
you get: "So we need to call useEffect here, then return null"
you say: "cube control get pods" (in a terminal)
you get: "kubectl get pods" (no capital, no period — it runs)
Both of those are real output from ov format, not an illustration — they are
asserted as tests in crates/ov-format/src/lib.rs.
You can run the formatter yourself without a microphone, a GPU, or the GUI:
cargo run -p ov-cli -- format "um so we need to call use effect here comma then return null"
cargo run -p ov-cli -- format "cube control get pods" --profile terminal --trace
It works the same in an email, a chat box, a document or a terminal. What changes is how it formats: OpenVoice knows which app has focus and applies the rules that app deserves.
One window and one floating pill. The window is where you teach it; the pill is the only part you see while you work.
The window comes in three frosted-glass themes — Glacier, Graphite and Lagoon — each in light and dark, picked in Settings → Appearance or left to follow Windows.
Local by default, network by exception. OpenVoice makes exactly two kinds of outbound request, both of which you start, and both are listed here: a speech model you press Download on, and an update check you can switch off (Settings → Updates). Nothing else. The default model ships in the installer, so a fresh install dictates offline without fetching anything. Every crate that touches your microphone, transcripts, keyboard or history is sealed — it has no path to a socket at all, and downloading lives in one separate crate that does. That is checked in CI, not just promised here. Every crate that touches your microphone, your transcripts, your keyboard or your history is sealed: it has no path to an HTTP client, TLS stack or socket library anywhere in its dependency graph. That is checked in CI, not just promised here.
Two honest caveats. The Tauri shell links reqwest transitively, because Tauri
does, so an HTTP client is present in the binary even though no OpenVoice code
calls it. And the update check is a genuine exception to "you asked for it" —
nobody asks to be told about a release. It fetches one signed manifest, carries
no identifier and no usage data, never installs anything on its own, and makes
no request at all when turned off. The reasoning, including why it defaults on,
is in ADR 0005.
The CI job names every permitted network dependency in an allow-list, so a new one cannot appear quietly — telemetry or a crash uploader still fails the build.
Never lose a word. If delivery fails, the text stays in OpenVoice for you to copy from Home. Recovery never copies automatically. Normal paste briefly borrows the clipboard, then restores its previous contents unless you copied something new.
Invisible when idle. ~60 MB RAM, ~0% CPU. You should never notice it running.
Deterministic where it can be. Formatting is rule-based and unit-tested. Probabilistic parts are isolated behind seams.
Your data is yours. History is a plain SQLite file at
%APPDATA%\OpenVoice\history.db with a documented
schema — open it with any SQLite browser, no
export feature required. (A built-in export is v0.3 work.) Recorded audio is
not kept unless you ask for it: the speech engine runs in-process, so audio
is decoded straight from memory and never written to disk. Turning on
— off by default, and there to diagnose a transcription
problem — writes them to instead,
where they are cleared after a week. Secrets matching
are stripped from history either way.
Right Ctrl ──► capture ──► Parakeet ──► format ──► inject at caret
(held) 16 kHz in-process rules SendInput /
mono CPU pipeline clipboard
Built as ports and adapters: the domain core has no dependency on the OS, audio, the GPU, or the GUI. Everything platform-specific sits behind one of six traits.
That isn't architecture for its own sake. It means the formatting rules — the part that actually determines whether this tool is good — can be tested in milliseconds with no microphone, no GPU, and no window manager. A rule change is verified in a second instead of by launching a GUI and talking to it.
The boundary is enforced mechanically: CI compiles the core crates for
wasm32-unknown-unknown, a target where none of those dependencies can link.
Six port traits are the entire contract surface — every one is declared in
ov-core/src/ports.rs, and nothing reaches the
operating system except through one of them. Adding a seventh requires an ADR.
| Crate | Role |
|---|---|
ov-core | Session state machine, the six ports, events, config. Pure. |
ov-format | Formatting pipeline, dictionary, voice commands. Pure. |
ov-audio | WASAPI capture via cpal; downmix and resample to 16 kHz mono |
ov-asr | Speech recognition, decoded in this process |
ov-fetch | Model downloads. The only crate that can open a socket |
ov-input | Keyboard hook, text injection, foreground app detection |
ov-store | SQLite history with FTS5 search |
ov-cli | ov — the same pipeline, headless. The integration harness |
ov-app | openvoice — the Tauri shell, and the composition root |
Full design: docs/ARCHITECTURE.md. Decisions and their
rationale: docs/adr/.
RTX 3050 Laptop (4 GB VRAM), Ryzen 5 6600H, decoding on the CPU:
| Model load, at startup | ~2.5–3.4 s |
| Key release to text, dictation under 3 s | ~245 ms typical |
| Key release to text, dictation over 15 s | ~420 ms typical (was ~2.2 s before 1.0.0) |
| Decoding left at release, after a natural pause | usually none |
| Memory while loaded | ~750 MB |
Since 1.0.0 a dictation is decoded while you speak, so the wait after you let go no longer grows with how long you talked. The release-to-text figures come from the first 1.0.0 session in the app; the benchmark on recorded speech, with accuracy before and after, is in docs/benchmarks/2026-09-13-release-latency.md.
Measured on the reference machine, CPU only, at four decode threads. Four rather than all twelve: the extra eight buy about 110 ms and cost the responsiveness of whatever you are dictating into.
Accuracy is deliberately not quoted as a number here. It was measured — see ADR 0008 — but on a public benchmark that is in-domain for this model, so the figure is a ceiling rather than a forecast, and a number in a README outlives that caveat.
Building from source needs considerably more: the Rust toolchain and MSVC build
tools come to roughly 14 GB, plus the model. See
CONTRIBUTING.md if that is a problem — it can all be
relocated to another drive.
Download OpenVoice-x64-setup.exe and run it. That link always
serves the newest build — it is deliberately not tied to a version number, because
a hand-written one goes stale the moment a release ships without someone
remembering to edit it. The releases page
has the version history.
Nothing to configure and no Python to install. The speech engine and its default model are both inside the installer, so OpenVoice works offline from the moment setup finishes — including the very first sentence. Two further models (multilingual, and a low-memory one) are optional and downloaded only if you ask for them on the Speech model screen. That is why the installer is around 550 MB: you download those bytes once, while you are already expecting to wait, rather than on first launch when you are trying to use the app.
Then hold Right Ctrl, speak, and release.
Two things worth knowing before you install:
The installer is not code-signed. Windows SmartScreen will warn about an unknown publisher, and you will have to click More info → Run anyway. A certificate is on the v0.5 roadmap. Because you are being asked to override that warning, every release ships a SHA-256 beside the installer and is built by a public GitHub Actions run from the tagged commit — so you can check that what you downloaded is what CI built:
Get-FileHash .\OpenVoice-x64-setup.exe -Algorithm SHA256
Compare that against the hash in the release notes and the .sha256 file
published next to the installer.
The bundled speech engine is CPU-only. The CUDA libraries are 1.9 GB — 88% of the dependency tree — and useless without an NVIDIA GPU, so they are not shipped. An installed copy runs on the CPU, which works everywhere but is markedly slower on the large model. To use the GPU today, run from source.
To uninstall, use Windows Add or remove programs; that removes the speech model
along with the app. Your history (%APPDATA%\OpenVoice\history.db) and settings
are left behind because they are yours — delete that folder if you want them gone
too.
# 1. Rust + MSVC build tools (Windows needs the C++ workload, not just VS Code)
winget install Rustlang.Rustup
winget install --id Microsoft.VisualStudio.2022.BuildTools `
--override "--quiet --add Microsoft.VisualStudio.Workload.VCTools --includeRecommended"
# 2. The speech model (~482 MB download, verified against a pinned SHA-256).
# There is no Python and no virtualenv any more; the engine links into the
# binary. This only fetches weights.
pwsh scripts/fetch-model.ps1
# 3. Frontend dependencies. This also installs the Tauri CLI used in step 5.
npm --prefix apps/ui ci
# 4. Run the tests. --test-threads=1 because each ov-asr test that touches the
# model loads ~750 MB, and running them in parallel needs several gigabytes.
cargo test --workspace -- --test-threads=1
# 5. Run it
cd crates/ov-app
node ../../apps/ui/node_modules/@tauri-apps/cli/tauri.js dev
The model is found in models/ in the checkout, or wherever OPENVOICE_MODEL_DIR
points. Nothing is downloaded at run time.
That sequence builds the full Windows app. You do not need any of it to work on
the parts that matter most: ov-core and ov-format are pure Rust and build and
test on any platform, with no MSVC, no GPU, and no microphone.
cargo test -p ov-core -p ov-format
The engine links into the binary, so the only extra payload is the model itself:
pwsh scripts/fetch-model.ps1 # ~482 MB, SHA-256 verified
$env:MODEL_SOURCE_DIR = "$PWD\models\parakeet-tdt-0.6b-v2"
cd crates/ov-app
node ../../apps/ui/node_modules/@tauri-apps/cli/tauri.js build
MODEL_SOURCE_DIR is read by
installer-hooks.nsh, which installs the
weights into the application directory. They are deliberately not a
bundle.resources entry: Tauri's updater downloads the whole installer on every
update, so a bundled model would turn every patch release into a ~550 MB download
for every user. Leave it unset and the installer builds without a model — useful
for testing packaging, useless to a user — which is why the release
workflow asserts the model is present before
bundling.
Details and troubleshooting: CONTRIBUTING.md.
OpenVoice installs a global keyboard hook and can synthesize keystrokes. Those are the same capabilities a keylogger has. You should be suspicious of any program that wants them, including this one.
What we do about that:
%TEMP%\openvoice\, deleted immediately after the decode — success or failure.
Nothing else writes audio to disk, and there is no retention path today.Found something wrong? SECURITY.md.
| v0.1 | Walking skeleton | hotkey → capture → transcribe → inject → history ✅ |
| v0.2 | The differentiator | formatting pipeline, dictionary, app profiles, settings UI ✅ |
| v0.3 | Feel | overlay waveform ✅, sound feedback ✅, history search ✅ — still to do: streaming partials, history export, sub-700 ms p50 |
| v0.4 | Intelligence | optional local LLM polish, prompt mode for AI agents |
| v0.5 | Distribution | published Windows installer ✅, auto-update ✅ — still to do: code signing, optional GPU pack, macOS |
| v1.0 | Stability | plugin API for formatter rules, frozen API |
Every phase ships something usable. None is a refactor-only phase.
Nothing in the settings is decorative any more. Transcript redaction, audio retention, toggle activation and the maximum-recording limit were all fields or toggles with no implementation behind them until v0.2.0; each now does what it says.
The Hub is frosted glass over Windows 11 Mica, in three themes that each come in
light and dark. The Flow Bar deliberately does not follow them: it floats over
other people's apps, so it is one design everywhere — obsidian glass, the logo's
seven bars at rest, no text, and colour only while the microphone is open. Then
the waveform runs from the logo's green through mint and cyan to periwinkle
(#44d62c → #52e3b0 → #5ad7f0 → #8aa8ff), and when your words land one pass of
light goes round the rim.
The whole system is a live page rather than a document. It needs no Rust and no Windows — the frontend runs standalone in any browser:
npm --prefix apps/ui ci
npm run dev:ui # then open http://localhost:5199/?window=sheet
?window=hub is the main window, ?window=overlay is the Flow Bar on its own,
?window=flowbar is every Flow Bar state at once, over the four kinds of
surface it has to stay legible against, and ?window=sheet is the original
component sheet.
Every screenshot in this README is captured from that same running UI by
scripts/screenshots.mjs, so none of them can drift
from the interface it claims to show. What the screens are reading is fixture
data from scripts/screenshot-fixtures.mjs —
the dictionary, profiles and model catalogue copied from the Rust sources they
mirror, the history rows taken from tests in ov-format, and one invented
month's worth of totals. Nothing here is a mocked component or a drawing of a
screen: the real Hub renders against the real invoke boundary, and only the
far side of it is canned. That is also why these are safe to recapture — the
previous versions came off a live machine and published whatever had last been
dictated into it. The PNGs are reduced to 256 colours afterwards, to keep the
repository small.
The pure crates are the easiest place to start, and they are also where the
interesting work is. ov-core and ov-format need no Windows, no GPU, no
microphone and no MSVC — cargo test -p ov-core -p ov-format is the whole setup. A
new formatting rule is about thirty lines plus two tests: one that would fail
without it, and one proving it does not fire when it shouldn't.
Good first things to look at: a missing term in
dictionary.rs (the model mistranscribes
some tool name you use — add what it actually hears), a voice command in
rules.rs, or an app profile for an editor nobody
has covered yet. Setup, the boundary rules, and how to write a rule that behaves:
CONTRIBUTING.md.
Wispr Flow and superwhisper are excellent and worth paying for. OpenVoice exists because I wanted something local, open, and tuned specifically for writing code and prompting agents.
Built on Parakeet TDT from NVIDIA NeMo, running on sherpa-onnx from k2-fsa. Earlier releases used faster-whisper and Whisper; see ADR 0008 for why that changed.
Name note: MyShell's OpenVoice is an unrelated and well-known text-to-speech project. No affiliation. A rename is under consideration.
%APPDATA%\OpenVoice\audioprivacy.redact_patterns