GUIDE

A Streamlit text to speech app with free offline voices

Streamlit turns a Python script into a web app, and with a text to speech engine that runs in the same process you get a voice app without any speech service, key or bill. This guide builds one in about 35 lines with the free SuperClonica engine: a text box, a voice and language choice, a player and a WAV download.

We tested the app with Streamlit’s own AppTest framework. Everything runs inside your Python process, so the texts never leave your computer or server.

Install

You need Python 3.10 or newer. Install both packages:

pip install streamlit superclonica-cpu

On the first run the engine downloads the Supertonic 3 model, about 400 MB; after that it works offline on an ordinary processor, and an NVIDIA graphics card only makes it faster.

The app

Save this as app.py:

import io, threading, wave
import numpy as np
import streamlit as st
from superclonica import Superclonica

VOICES = ["F1", "F2", "F3", "F4", "F5", "M1", "M2", "M3", "M4", "M5"]
LANGUAGES = {"English": "en", "Español": "es", "Deutsch": "de", "Français": "fr", "Русский": "ru", "日本語": "ja"}

@st.cache_resource
def engine():
    return Superclonica(), threading.Lock()

def to_wav(audio, rate):
    pcm = (np.clip(np.asarray(audio, dtype=np.float32).reshape(-1), -1, 1) * 32767).astype(np.int16)
    buffer = io.BytesIO()
    with wave.open(buffer, "wb") as file:
        file.setnchannels(1)
        file.setsampwidth(2)
        file.setframerate(rate)
        file.writeframes(pcm.tobytes())
    return buffer.getvalue()

st.title("Text to speech")
text = st.text_area("Text", max_chars=2000)
voice = st.selectbox("Voice", VOICES)
language = st.selectbox("Language", list(LANGUAGES))

if st.button("Voice it", disabled=not text.strip()):
    tts, lock = engine()
    with st.spinner("Voicing..."), lock:
        audio, rate = tts.synthesize(text, voice=voice, lang=LANGUAGES[language])
    wav = to_wav(audio, rate)
    st.audio(wav, format="audio/wav")
    st.download_button("Download WAV", wav, file_name="speech.wav", mime="audio/wav")

Start it and open the address it prints:

streamlit run app.py

st.cache_resource creates the engine once for all visitors instead of on every rerun, and the lock makes requests from several people take turns. The button stays disabled until there is text, and st.download_button hands the same WAV to the visitor.

Voices, languages and speed

The list holds the ten stock voices, M1 to M5 and F1 to F5. To add a voice from the SuperClonica catalog, put the path of its voice file in the list; listen to it first on its page, where a line of 30 to 100 characters is voiced free. Add language codes to the dictionary for any of the 31 supported languages; Chinese is not supported yet. Speed can be set on the engine, for example tts.speed = 1.1, from 0.7 to 2.0.

Share it

Streamlit Community Cloud can deploy the app from a GitHub repository: add a requirements.txt that lists superclonica-cpu. In a public app keep max_chars low, and offer only voices you may share: the stock voices are free to use under the model license, while catalog voices you bought are for your own projects. If you would rather not run the model at all, call the SuperClonica speech API from the same button instead.