From 79250f1fe087dd5d530425270e0c4f63da28d158 Mon Sep 17 00:00:00 2001 From: filipi87 Date: Wed, 22 Apr 2026 14:20:30 -0300 Subject: [PATCH] Making includes_inter_frame_spaces optional for word-timestamp. --- changelog/4330.changed.md | 4 ++-- src/pipecat/services/tts_service.py | 12 +++++++----- 2 files changed, 9 insertions(+), 7 deletions(-) diff --git a/changelog/4330.changed.md b/changelog/4330.changed.md index 97eb2406c..839357a16 100644 --- a/changelog/4330.changed.md +++ b/changelog/4330.changed.md @@ -1,2 +1,2 @@ -- added `includes_inter_frame_spaces` to `TTSService` and `WebsocketTTSService`, with default to `false` to preserve existing behaviors. -- `InworldTTSService` to set `includes_inter_frame_spaces` to `true` to stop inserting spaces between words from server, which already include spaces. \ No newline at end of file +- Added `includes_inter_frame_spaces` parameter to `TTSService.add_word_timestamps` and `_add_word_timestamps` (default `None`). When `True`, downstream consumers will not inject additional spaces between tokens; `None` leaves each frame's own default unchanged. +- `InworldTTSService` now passes `includes_inter_frame_spaces=True` when reporting word timestamps, since Inworld tokens already include inter-word spacing. \ No newline at end of file diff --git a/src/pipecat/services/tts_service.py b/src/pipecat/services/tts_service.py index cfc8d784f..fa5981802 100644 --- a/src/pipecat/services/tts_service.py +++ b/src/pipecat/services/tts_service.py @@ -96,7 +96,7 @@ class _WordTimestampEntry: word: str timestamp: float context_id: str - includes_inter_frame_spaces: bool = False + includes_inter_frame_spaces: bool | None = None class TTSService(AIService): @@ -1066,7 +1066,7 @@ class TTSService(AIService): self, word_times: list[tuple[str, float]], context_id: str | None = None, - includes_inter_frame_spaces: bool = False, + includes_inter_frame_spaces: bool | None = None, ): """Add word timestamps for processing. @@ -1080,7 +1080,8 @@ class TTSService(AIService): context_id: Unique identifier for the TTS context. includes_inter_frame_spaces: When True, the tokens already embed inter-word spacing (spaces and punctuation are part of the token text). Downstream - consumers must not inject additional spaces between tokens. + consumers must not inject additional spaces between tokens. None leaves + the frame's own default unchanged. """ if context_id and self.audio_context_available(context_id): for word, timestamp in word_times: @@ -1104,7 +1105,7 @@ class TTSService(AIService): self, word_times: list[tuple[str, float]], context_id: str | None = None, - includes_inter_frame_spaces: bool = False, + includes_inter_frame_spaces: bool | None = None, ): """Process word timestamps directly, building and pushing TTSTextFrames inline. @@ -1125,7 +1126,8 @@ class TTSService(AIService): ) else: frame = TTSTextFrame(word, aggregated_by=AggregationType.WORD) - frame.includes_inter_frame_spaces = includes_inter_frame_spaces + if includes_inter_frame_spaces is not None: + frame.includes_inter_frame_spaces = includes_inter_frame_spaces frame.pts = self._initial_word_timestamp + ts_ns frame.context_id = context_id if context_id in self._tts_contexts: