diff --git a/speech.py b/speech.py index 1dff98c..7878746 100755 --- a/speech.py +++ b/speech.py @@ -1295,39 +1295,33 @@ async def generate_speech(request: GenerateSpeechRequest): logger.info(f"Loading F5-TTS model on device '{device}'") f5_model = await asyncio.to_thread(f5_wrapper, device=device) - # Split text into sentences for streaming (first audio arrives faster) - sentences = simple_sentence_split(input_text, max_length=500) - logger.info(f"Split text into {len(sentences)} sentences for F5-TTS streaming") + # F5-TTS handles long text via internal chunking. Per-sentence splitting + # produces a ref-to-gen transition artifact at the start of EACH chunk + # (audible as gibberish/tinny prefix). Pass full text as one inference. + logger.info(f"F5-TTS processing {len(input_text)} chars as single inference") # F5-TTS outputs float32 PCM at 24kHz ffmpeg_args = build_ffmpeg_args(response_format, input_format="f32le", sample_rate="24000") - - # F5-TTS accepts speed natively; only apply atempo as a fallback when ffmpeg can do it cheaper - # (we pass speed to the model below, leaving ffmpeg speed at 1.0) - ffmpeg_args.extend(["-"]) ffmpeg_proc = subprocess.Popen(ffmpeg_args, stdin=subprocess.PIPE, stdout=subprocess.PIPE) in_q = queue.Queue() def generator(): - """Process sentences sequentially and feed to queue""" + """Run F5-TTS once for the full input text""" try: - for idx, sentence in enumerate(sentences): - logger.debug(f"F5-TTS processing sentence {idx+1}/{len(sentences)}: {len(sentence)} chars") - audio_bytes = f5_model.tts( - text=sentence, - ref_audio=ref_audio, - ref_text=ref_text, - speed=speed, - ) - in_q.put(audio_bytes) - logger.debug(f"F5-TTS: queued sentence {idx+1}/{len(sentences)}") + audio_bytes = f5_model.tts( + text=input_text, + ref_audio=ref_audio, + ref_text=ref_text, + speed=speed, + ) + in_q.put(audio_bytes) except Exception as e: - logger.error(f"F5-TTS streaming error: {e}") + logger.error(f"F5-TTS generation error: {e}") finally: in_q.put(None) - logger.info(f"F5-TTS streaming complete: {len(sentences)} sentences processed") + logger.info("F5-TTS generation complete") def out_writer(): """Write audio from queue to ffmpeg stdin"""