Dev.to AI πŸ€– Ai πŸ‘ 0 πŸ“– 4 min read

Signal2Speech: getting ready for a real EEG board (Update 4)

This is our fourth update on Signal2Speech, our Hack the Nest 2026 project that lets someone answer questions with an EEG headset. The app suggests replies, the wearer picks one with a P300 response (a brain signal that

This is our fourth update on Signal2Speech, our Hack the Nest 2026 project that lets someone answer questions with an EEG headset. The app suggests replies, the wearer picks one with a P300 response (a brain signal that shows up about 300 milliseconds after the tile you're watching flashes), and they confirm by closing their eyes. Nothing is spoken until they confirm. Our own headset was lost in transit, but there is a PiEEG Octopus 16 board on the venue library's first floor. Most of the last two hours went into getting ready to test on it with an actual person.

One command for the board session

Time on the board is limited, so we built one command that runs the whole session, and the wearer only has to listen. Every instruction is spoken out loud, and then a beep starts the timed part, so the timing doesn't depend on how fast anyone reads. The session has six phases in about 5 minutes: pin contact, which pins respond, calibration, false triggers at rest, an eye-closure test, and a four-choice test. Raw data is recorded from the first second and saved after every phase, so a nothing is lost if it fails halfway. A separate check makes sure the saved recording is complete before we leave the board. The session also needs a consent flag since we are recording someone's brain data.

The four-choice test works differently from our two-tile P300 setup. This board gives one dependable signal, which is the eyes-closed alpha rhythm. Because of this, the app reads the choices out loud one at a time ("One: Yes. Two: No…"), and the wearer closes their eyes on the one they want, then once more to confirm. On our simulated 16-pin stream, a full pick and confirm from four choices took about 19 seconds. We also tested it with slow and uneven reactions, with almost no eyes-closed response (it stops with a clear reason), and with the board dropping out (it stops within 3 seconds). None of this has run on a real board or a real person yet.

The PiEEG board in the real app

The real app can now use a PiEEG board's eye closure as the confirm. Keys pick the answer, then closing your eyes for two seconds confirms it, and finally the map changes once. Eye confirm only turns on after the board check passes on screen in that same session. If the check fails, holding key 1 confirms instead.

One problem with this setup is that the data stream itself can't prove where it came from, so a simulator could look exactly like a real board. Because of this, you have to say what is sending the signal (live, simulated, or recorded) when starting the app. That way, a simulator can never show up as Live EEG. The bottom strip now names both inputs, for example "Choose: Keyboard Β· Confirm: Live EEG (PiEEG Octopus 16)."

A confirm ring and sound cues

The "Say this?" screen now shows the exact words as a big quote, says what will happen ("This will be said aloud" or "This will show the map and say"), and has a ring that fills toward the confirm. Nothing is spoken until the ring is full. On the keyboard, you now hold 1 for 2 seconds, since a quick tap could confirm by accident. With EEG, the ring follows the eye-closure signal and empties if the eyes open early.

We also added short, quiet tones for preview, confirm, and cancel. A wearer with their eyes closed can't see the screen, so the tones are how they know their pick actually registered. The confirm tone ends before speech starts so they never overlap. The panel under the map also reads like a conversation now (Options, Previewed, Said aloud, or Nothing was said), with the input that caused each step.

A voice bug we only found by accident

While building the board session, we noticed the spoken cues went silent after the first one. The speech library we use as a backup voice (pyttsx3) was speaking the first reply and silently skipping every one after it. It was never noticed in the app because the judging laptop uses Qt's Windows voice instead, which was never affected. However, on any machine that falls back to the backup voice, the wearer would only ever hear their first answer, which could lead to them thinking a later answer was spoken when it actually wasn't. The fix speaks each reply from its own short-lived helper process, which also stops the window from freezing while it talks. Before the fix, the backup spoke for 2.9 seconds, then 0.1 and 0.1. After it, it spoke for 2.7, 2.3, and 2.2 seconds.

Smaller things

  • Window size: The app used to open at 1700 Γ— 900, which ran off the judging laptop's screen at 125% scaling. It now opens inside whatever screen it's on.
  • Honest wording: Our Devpost draft said Claude "can't invent numbers." That is only true for map answers, which speak our own fixed lines. Ordinary replies are the model's own words kept to the facts by the prompt, so the draft now says exactly that.
  • README: The status table now says the app already takes live headset input, since it still said live input was switched off.

What's next

Next, we are taking the judging laptop to the library and running the board session with an actual person. After that, we are recording the demo video and submitting the final version on Devpost.

Repo: https://github.com/Order-of-the-Golden-Eagles/Signal2Speech

πŸ“° Read the original article on Dev.to AI

Originally published by Dev.to AI. Aggregated on AIWithGhost for educational purposes β€” full credit and traffic to the original publisher.