Back to the dev blog Engineering update

The road to SyncTrans 1.0: building a real-time interpreter for the Mac

Read this article in: English · 中文 · 日本語 · Español · Français · 한국어 · Українська

SyncTrans 1.0.0 shipped this week. It is a real-time speech translator for macOS 14 and later, running on Apple Silicon: you speak, the translation appears as the sentence forms, and a synthesized voice reads it aloud. This post is the engineering account of how it got here — what we built, in what order, and which tradeoffs we accepted. The short user-facing notes live in What's New.

Why build an interpreter for the Mac

The translation apps on phones work well for asking where the bathroom is. They work much less well for an actual conversation, because they turn the conversation into two people taking turns staring at a small screen and handing the device back and forth. The conversations we cared about — a client meeting, a consultation, a family discussion with a lawyer or a doctor — have a laptop on the table more often than they have a phrasebook.

A Mac also happens to be unusually good hardware for this job. Apple Silicon can run speech recognition, machine translation, and speech synthesis locally at interactive speed, and the machine already has a good microphone path, real speakers, and as many displays as you want to plug in. The goal we set was simple to say: the machine handles the language, so the people can handle the conversation.

Two engine families, developed in parallel

From the first prototype, SyncTrans had two ways to do the same job. The managed cloud engine needs no setup: sign in, pick languages, start. The on-device engine runs recognition, translation, and synthesis entirely on the Mac — nothing leaves the machine, and it keeps working without a network.

We deliberately built both at the same time rather than shipping the cloud path first and bolting on local inference later. The cost was real: every feature had to work twice, over two very different stacks. The payoff was a single engine abstraction that both stacks plug into, and a habit of measuring instead of asserting. Every local model tier carries a measured memory floor, and the app checks what the machine can actually run before offering it — an older Mac is told honestly which tiers are out of reach instead of being routed somewhere that would swap.

The third engine option fell out of that abstraction almost for free: if you already have speech and translation services you trust, you can point SyncTrans at your own API endpoints and the rest of the app works unchanged. Three engines, one interface, and switching between them is a settings choice, not a reinstall.

Designed for the face-to-face case

The feature that shaped the product most came from watching people use early builds. Given a single window, two speakers inevitably angled the screen back and forth. So 1.0 ships a dual-screen conversation view: put one language full-screen on each display, set the Mac between the speakers, and each person reads the screen meant for them. Each window can be assigned to its own display from inside the app.

The audio got the same treatment. With a shared pair of headphones, SyncTrans can send one language to the left ear and the other to the right, so two people sharing one Mac each hear the translation meant for them. It is a small thing to describe and a surprisingly large thing in practice: the conversation stops being about the machine at all.

Three layouts over one session record

Different moments want different views of the same conversation, so 1.0 ships three layouts over a single underlying session record. The chat layout interleaves both languages turn by turn, the way a messaging app does. The dual-column layout gives each language its own column, which reads better when two people follow along at once. The meeting-minutes layout renders the session as a running document you can skim like notes. Because the layouts are views over one record, switching mid-session loses nothing.

Glossary, context, and numbers that behave

Two quality features made it into 1.0 because they matter more than raw model choice. Translation runs with rolling conversation context, so pronouns and topic references resolve against what was actually said earlier in the session. A per-project glossary pins the words a model would otherwise guess at: product names, people's names, technical terms. Once a term is in the glossary, it comes out the same way every time.

1.0 also includes a deterministic rule layer that sits behind the model for numbers and discount phrasing, where a literal translation can quietly invert the meaning — Chinese discount conventions are the famous case. That work has its own post: Numbers that survive translation.

History you can search and export

A translated conversation is often something you need afterwards, so every session is saved per project on the Mac. History is searchable across projects, individual turns can be corrected or deleted, and a finished session exports as TXT, Markdown, or SRT — meeting notes, a quote you need in writing, or subtitles for a recording of the same event. The record lives on your machine, whichever engine produced it.

Seven languages in the interface

An interpreter whose interface only speaks one language has a credibility problem, so the 1.0 interface is localized into seven: English, Chinese, Japanese, Spanish, French, Korean, and Ukrainian. We treated localization as engineering work rather than a translation dump — toolbar labels that truncate, buttons that grow past their containers, and layouts that only fit English all got audited and fixed. This blog is published in the same seven languages, which felt like the honest way to do it.

What 1.0 means

For us, 1.0 is a baseline promise: the full loop — speak, see, hear, keep — works end to end on every engine we ship, on the hardware we say it works on. SyncTrans 1.0.0 needs macOS 14 or later on Apple Silicon, and you can download it here. The feature tour is on the Features page.

Questions or bug reports? The feedback board is the fastest way to reach us.