Skip to content
M1KUAPPPublic

Repository files navigation


Turn banner

Turn

An AAC iPhone app that listens to a conversation partner and suggests replies from the user's own saved phrases, so they can answer in time.
Try the Simulator Build » · Demo Video · Report a Bug

TypeScript Swift React React Native Expo Bun SQLite RevenueCat Cloudflare Workers Vitest Prettier

Table of Contents

Expand
  1. About The Project
  2. Getting Started
  3. Roadmap
  4. Team
  5. License
  6. Acknowledgments

About The Project

Your own words, in time for your turn. Turn is an augmentative and alternative communication (AAC) app for iPhone, for adults who can read and tap but can't rely on their speech, such as people living with ALS or recovering from a stroke. It speaks their saved phrases and typed words aloud. In Listen mode, when a conversation partner finishes speaking, a row above the grid offers the person's own saved phrases that answer what was said, so they can reply before the conversation moves on.

A hosted decision model chooses which of the person's phrases answer each line, and whether any do. It never writes a word, and nothing speaks until the person taps. Speaking is always free; Turn Listen, a one-time purchase through RevenueCat, keeps Listen mode on after 20 free partner lines.

On September 23, 2026, at commit 213f488, the team evaluated 80 partner lines. On the 64 lines with an acceptable saved reply besides Yes, No, and Not sure:

Ranker Top 1 Top 6 Mean reciprocal rank
chance 5% 26% 0.15
place 1 of 64, 1.6% (0.3% to 8.3%) 8 of 64, 13% (6.5% to 23%) 0.06
keyword 10 of 64, 16% (8.7% to 26%) 15 of 64, 23% (15% to 35%) 0.19
embeddings 14 of 64, 22% (14% to 33%) 29 of 64, 45% (34% to 57%) 0.34
hosted decision model 43 of 64, 67% (55% to 77%) 48 of 64, 75% (63% to 84%) 0.72

Claude subagents wrote the lines, the starter bank, and the acceptable-reply labels at the team's direction. The evaluation report has the intervals, the row's risk and coverage, latency, and who wrote what.

Built for RevenueCat Shipaton 2026.

↑

Screenshots

Clinic speaking grid with the conversation strip, Quick phrases, and floating Type, Repeat, Up, and Down toolbar
Speaking Grid · The Clinic grid of saved phrases, with the conversation strip and floating toolbar.
Partner consent card explaining Listen mode, with an under-18 switch and They agreed and They said no buttons
Partner Consent · The consent card the partner sees each time listening starts, with an under-18 switch.
Clinic reply row offering It went well, It was hard, It’s getting worse, and I’m good, thanks after How was physio?
Suggested Replies · Saved phrases that answer what the partner said, in a row above the grid.
Chat phrase bank with starter phrases, pencil edit buttons, and controls to reorder or add phrases
Phrase Bank Editor · A category's starter phrases, with buttons to edit, reorder, or add phrases.
Turn Listen paywall showing Keep Listen mode on, a US$24.99 one-time purchase, and Restore Purchases
Turn Listen Paywall · A one-time purchase that keeps Listen mode on after 20 free partner lines.
Settings with voice and speech rate, Companion Off, Listen service Working, places, phrase bank, and purchase options
Settings · Voice and speech rate, companion, Listen service status, places, phrase bank, and purchases.
Companion settings with Ren, Suit, Office, and Ice face choices and Let it move
Choose a Companion · Choose Ren, Suit, Office, or Ice, and whether the face moves.
Ren beside Home’s floating toolbar, below the Quick phrase grid
Home with Ren · Ren sits beside the floating toolbar and mouths what Turn says.
Partner view with Ren, I have something to say in big text, and Say it again
Partner View · Tapping the face shows your line in big text, with Say it again.

↑

How It Works

  1. Pick a place. On first launch, tap Review to edit the starter phrases, or Not now to try them as supplied. The speaking grid has about 150 phrases in categories. Tap Home at the top of the grid and choose Clinic.

    Place menu with Home selected, Clinic, Shop, Out, and Edit places
  2. Speak. Tap any phrase to hear it in a system voice or your Personal Voice. Tap Type to speak typed words, which join the phrase bank. If iOS shows its typing tutorial, tap Continue.

    Type composer with I need a break, the Speak button, and the iOS keyboard
  3. Start Listen mode. Tap Listen, then Allow to let Turn send your phrases and the partner's words to the hosted decision model. Show the partner the consent card and tap They agreed.

    Before Listen mode starts sheet explaining what is sent to the AI service, with the privacy notice, Allow, and Not now
  4. Answer. In the Simulator build, the partner's line is typed; on an iPhone, Turn can also transcribe the partner's speech. Tap Tap here to type what they say., enter "How was physio?", and tap Send. "It was hard" appears in the row of suggested replies, though the two share no content word. Tap it to say it; Repeat changes to Stop while Turn speaks.

    How was physio? above four saved replies including It was hard
  5. Keep listening. Listen mode answers 20 partner lines for free; the 21st opens the Turn Listen paywall. To buy it, open Settings, tap Unlock Listen mode, and complete the purchase in RevenueCat's Test Store. Restore Purchases in Settings refreshes the status after a reinstall.

    Turn Listen paywall with the US$24.99 one-time price, Unlock Listen mode, Restore Purchases, and privacy notice

↑

Features

  • A speaking grid of your own words. Saved phrases in categories you can rename and reorder, about 150 editable starter phrases, and typed replies that join the bank.
  • Your voice. Speaks in your Personal Voice, if you made one in iOS, or a system voice.
  • Replies from what the partner said. One big button when Turn is confident, up to six replies otherwise, and no change when nothing fits. Yes, No, and Not sure come first for a yes-or-no question and always keep their places.
  • A steady row. A reply keeps its slot until a new one wins by a clear margin, and the grid never reorders itself.
  • A conversation strip. Five fixed phrases that manage the conversation, such as "Wait, I'm typing" and "Sorry, say that again".
  • A face for your voice. In Settings → Companion, choose Ren, Suit, Office, or Ice; the companion is Off by default. Beside the toolbar, the face mouths what Turn says, looks up while the partner’s words arrive, and looks down while you type.
  • A view for the partner. Tap the face to show the spoken line in big text with Say it again. In each place’s sheet, Show the face here turns the face on or off for that place.
  • A face that moves with you. The live Live2D face breathes and its hair follows its physics when Let it move is on and Reduce Motion is off. Otherwise, it holds still.
  • Listening that's agreed and visible. Your permission before any phrase leaves the phone, the partner's consent card each time listening starts, a light while it listens, and a switch that keeps a partner under 18 from being heard.
  • Private by default. No accounts; the phrase bank stays on the phone, names become tags before a line leaves it, and no audio is recorded. The privacy notice is also in the app, under Settings and About.
  • Useful offline. Without a network, or when the model service is slow or down, the phone ranks phrases itself and says Listen mode is degraded.
  • Speech is never sold. The grid, typing, saved phrases, and Personal Voice are free; Turn Listen is sold once.

↑

Architecture

Turn architecture

Made with Archify from architecture.json.

↑

Tech Stack

  • Languages: TypeScript and Swift.
  • Frontend: Expo SDK 57, React Native 0.86, React 19.2, Expo Router, expo-speech, and expo-speech-recognition; Swift Expo modules for on-device transcription with SpeechAnalyzer (turn-listen) and Personal Voice (turn-voice); and the shortlist and the relay's types in packages/shared, with MiniSearch for the phone's own ranking.
  • Backend: the relay, a Cloudflare Worker with SQLite-backed Durable Objects, in apps/relay.
  • Data: expo-sqlite on the phone.
  • AI and services: RevenueCat's react-native-purchases and react-native-purchases-ui, with the Test Store, and its REST API v2 on the relay; and, for the evaluation, Workers AI embeddings and Apple's sentence embeddings through Swift.
  • Tooling: Bun workspaces, Vitest, Prettier, Husky with commitlint, Maestro flows, and the evaluation's Bun scripts in packages/eval.

↑

Getting Started

Install the Simulator build to try Turn, or build it from source, with no keys of your own; live transcription needs a physical iPhone, while the Simulator build takes typed partner lines.

↑

Prerequisites

  • iOS 26+ — Turn runs on it.
  • Xcode 27 — on a Mac, with the iOS 27 Simulator runtime, to run Turn in the Simulator.
  • Bun 1.4.2 — to build from source.
  • CocoaPods — to build from source.
  • Cloudflare account — to run your own relay.
  • RevenueCat project with a listen entitlement — to run your own relay.
  • Hosted decision model API key — to run your own relay or the evaluation.
  • Cloudflare Workers AI credentials — to run the evaluation.
  • Swift — to run the evaluation's Apple sentence embeddings.

↑

Installation

  1. The Simulator build. Download Turn.app.zip from the latest release, boot an iOS 27 Simulator, and install it. It embeds its JavaScript, so it runs without Metro.

    unzip Turn.app.zip
    xcrun simctl install booted Turn.app
    xcrun simctl launch booted com.m1ku.turn
  2. From source. Clone the repository, install, and run the app on a Simulator. Leave Metro running.

    git clone https://github.com/M1KUAPP/Turn.git
    cd Turn
    bun install --frozen-lockfile
    cd apps/mobile
    bun run ios

    For a physical iPhone, set EXPO_PUBLIC_BUILD_KIND=device and run bunx expo run:ios --device, with your own signing team.

  3. With your own keys. The app is configured with the team's public Test Store key and relay. To use your own, copy apps/relay/.dev.vars.example to apps/relay/.dev.vars, fill in its three secrets, and set your RevenueCat project and entitlement IDs in apps/relay/wrangler.jsonc. Then start the relay:

    cd apps/relay
    bunx wrangler dev --port 8787

    In apps/mobile/.env, set EXPO_PUBLIC_RELAY_URL=http://localhost:8787 and your public Test Store key, then build the app as above. Secret keys stay in the relay.

  4. The evaluation. Set the environment variables that packages/eval/src/report.ts documents, then run it from a clean commit. It makes paid model calls and writes a report with its plots.

    bun run eval --unnamed --out packages/eval/your-results.md
  5. Run the checks. Run this from the repository root to check a change: it runs the lint, typecheck, and tests.

    bun run check

↑

Roadmap

See open issues for a full list of proposed features (and known issues).

↑

Team

Turn team

Made with contrib.rocks.

↑

License

See LICENSE for more information.

↑

Acknowledgments

↑

Releases

Contributors

Languages