speech-to-speech 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +661 -0
- package/README.md +591 -0
- package/dist/index.cjs +1163 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +2 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.mjs +1118 -0
- package/dist/index.mjs.map +1 -0
- package/dist/stt/index.cjs +668 -0
- package/dist/stt/index.cjs.map +1 -0
- package/dist/stt/index.d.cts +142 -0
- package/dist/stt/index.d.ts +142 -0
- package/dist/stt/index.mjs +664 -0
- package/dist/stt/index.mjs.map +1 -0
- package/dist/tts/index.cjs +500 -0
- package/dist/tts/index.cjs.map +1 -0
- package/dist/tts/index.d.cts +215 -0
- package/dist/tts/index.d.ts +215 -0
- package/dist/tts/index.mjs +458 -0
- package/dist/tts/index.mjs.map +1 -0
- package/package.json +92 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/stt/reset-stt-logic.ts","../src/stt/vad-controller.ts","../src/stt/stt-logic.ts","../src/tts/prepare-piper-voice.ts","../src/tts/stream-tokens-to-speech.ts","../src/tts/ort-setup.ts","../src/tts/piper.ts","../src/tts/use-streaming-tts.ts","../src/tts/piper-synthesizer.ts","../src/tts/audio-player.ts"],"names":["ResetSTTLogic"],"mappings":"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","file":"index.mjs","sourcesContent":["export type ResetReason = \"silence\" | \"utterance-complete\" | \"manual\";\r\n\r\nexport interface ResetStats {\r\n utteranceStartedAt: number;\r\n lastActivityAt: number;\r\n partialTranscript: string;\r\n}\r\n\r\nexport interface ResetSTTOptions {\r\n /** Maximum silence (ms) allowed before forcing a reset. */\r\n maxSilenceMs?: number;\r\n /** Maximum utterance length (ms) before rotating to a fresh buffer. */\r\n maxUtteranceMs?: number;\r\n /** Optional reset hook for logging/analytics. */\r\n onReset?: (reason: ResetReason, stats: ResetStats) => void;\r\n /**\r\n * Supply a clock for deterministic tests; defaults to Date.now.\r\n * Using a function keeps the class platform-neutral.\r\n */\r\n now?: () => number;\r\n}\r\n\r\n/**\r\n * Tracks speech activity and decides when to reset an STT pipeline so tokens and streams do not grow unbounded.\r\n */\r\nexport class ResetSTTLogic {\r\n private readonly maxSilenceMs: number;\r\n private readonly maxUtteranceMs: number;\r\n private readonly onReset?: (reason: ResetReason, stats: ResetStats) => void;\r\n private readonly now: () => number;\r\n\r\n private utteranceStartedAt: number;\r\n private lastActivityAt: number;\r\n private partialTranscript = \"\";\r\n\r\n constructor(options: ResetSTTOptions = {}) {\r\n this.maxSilenceMs = options.maxSilenceMs ?? 2000;\r\n this.maxUtteranceMs = options.maxUtteranceMs ?? 15000;\r\n this.onReset = options.onReset;\r\n this.now = options.now ?? (() => Date.now());\r\n\r\n const start = this.now();\r\n this.utteranceStartedAt = start;\r\n this.lastActivityAt = start;\r\n }\r\n\r\n recordSpeechActivity(timestamp?: number): void {\r\n const now = timestamp ?? this.now();\r\n this.lastActivityAt = now;\r\n if (!this.utteranceStartedAt) {\r\n this.utteranceStartedAt = now;\r\n }\r\n }\r\n\r\n updatePartialTranscript(partial: string, timestamp?: number): void {\r\n this.partialTranscript = partial;\r\n this.recordSpeechActivity(timestamp);\r\n }\r\n\r\n shouldReset(timestamp?: number): ResetReason | null {\r\n const now = timestamp ?? this.now();\r\n const silenceElapsed = now - this.lastActivityAt;\r\n const utteranceElapsed = now - this.utteranceStartedAt;\r\n\r\n if (silenceElapsed >= this.maxSilenceMs) {\r\n return \"silence\";\r\n }\r\n\r\n if (utteranceElapsed >= this.maxUtteranceMs) {\r\n return \"utterance-complete\";\r\n }\r\n\r\n return null;\r\n }\r\n\r\n maybeReset(timestamp?: number): ResetReason | null {\r\n const reason = this.shouldReset(timestamp);\r\n if (reason) {\r\n this.reset(reason, timestamp);\r\n }\r\n return reason;\r\n }\r\n\r\n forceReset(reason: ResetReason = \"manual\", timestamp?: number): void {\r\n this.reset(reason, timestamp);\r\n }\r\n\r\n private reset(reason: ResetReason, timestamp?: number): void {\r\n const now = timestamp ?? this.now();\r\n const stats: ResetStats = {\r\n utteranceStartedAt: this.utteranceStartedAt,\r\n lastActivityAt: this.lastActivityAt,\r\n partialTranscript: this.partialTranscript,\r\n };\r\n\r\n this.utteranceStartedAt = now;\r\n this.lastActivityAt = now;\r\n this.partialTranscript = \"\";\r\n\r\n if (this.onReset) {\r\n this.onReset(reason, stats);\r\n }\r\n }\r\n}\r\n","import { MicVAD, getDefaultRealTimeVADOptions } from \"@ricky0123/vad-web\";\r\n\r\nexport type VADControllerOptions = {\r\n bufferSize?: number;\r\n minSpeechMs?: number;\r\n minSilenceMs?: number;\r\n energyThreshold?: number;\r\n dynamicThresholdFactor?: number;\r\n noiseFloorSmoothing?: number;\r\n noiseFloorDecay?: number;\r\n maxAmplitude?: number;\r\n};\r\n\r\nexport class VADController {\r\n private vad: MicVAD | null = null;\r\n private voiceStartListeners = new Set<() => void>();\r\n private voiceStopListeners = new Set<() => void>();\r\n private running = false;\r\n private options?: VADControllerOptions;\r\n\r\n constructor(options?: VADControllerOptions) {\r\n this.options = options;\r\n }\r\n\r\n public async start(): Promise<void> {\r\n if (this.running && this.vad) {\r\n if (!this.vad.listening) {\r\n await this.vad.start();\r\n }\r\n return;\r\n }\r\n\r\n if (\r\n typeof navigator === \"undefined\" ||\r\n !navigator.mediaDevices ||\r\n !navigator.mediaDevices.getUserMedia\r\n ) {\r\n throw new Error(\"Microphone access is not available.\");\r\n }\r\n\r\n try {\r\n const ortAny = (window as any).ort;\r\n if (ortAny && ortAny.env && ortAny.env.wasm) {\r\n ortAny.env.wasm.wasmPaths = \"/ort/\";\r\n }\r\n\r\n if (!this.vad) {\r\n const defaultOptions = getDefaultRealTimeVADOptions(\"v5\");\r\n \r\n // Configure custom options\r\n this.vad = await MicVAD.new({\r\n ...defaultOptions,\r\n startOnLoad: false,\r\n onSpeechStart: () => {\r\n this.emitVoiceStart();\r\n },\r\n onSpeechEnd: (audio: Float32Array) => {\r\n this.emitVoiceStop();\r\n },\r\n onVADMisfire: () => {\r\n },\r\n minSpeechMs: this.options?.minSpeechMs || 150,\r\n positiveSpeechThreshold: 0.5,\r\n negativeSpeechThreshold: 0.35,\r\n redemptionMs: this.options?.minSilenceMs || 450,\r\n preSpeechPadMs: 50,\r\n processorType: \"ScriptProcessor\",\r\n\r\n onnxWASMBasePath: \"/ort/\",\r\n baseAssetPath: \"/vad/\",\r\n workletOptions: {},\r\n });\r\n }\r\n\r\n if (!this.vad.listening) {\r\n await this.vad.start();\r\n }\r\n \r\n this.running = true;\r\n } catch (error: any) {\r\n this.running = false;\r\n throw new Error(\r\n error?.message || \"Failed to initialize voice activity detector\"\r\n );\r\n }\r\n }\r\n\r\n public stop(): void {\r\n if (!this.running || !this.vad) return;\r\n try {\r\n this.vad.pause();\r\n this.running = false;\r\n } catch (error) {\r\n }\r\n }\r\n\r\n public destroy(): void {\r\n this.stop();\r\n if (this.vad) {\r\n try {\r\n this.vad.destroy();\r\n } catch (error) {\r\n }\r\n this.vad = null;\r\n }\r\n this.voiceStartListeners.clear();\r\n this.voiceStopListeners.clear();\r\n }\r\n\r\n public isActive(): boolean {\r\n return this.running && this.vad !== null && this.vad.listening;\r\n }\r\n\r\n public onVoiceStart(listener: () => void): () => void {\r\n this.voiceStartListeners.add(listener);\r\n return () => this.voiceStartListeners.delete(listener);\r\n }\r\n\r\n public onVoiceStop(listener: () => void): () => void {\r\n this.voiceStopListeners.add(listener);\r\n return () => this.voiceStopListeners.delete(listener);\r\n }\r\n\r\n private emitVoiceStart(): void {\r\n this.voiceStartListeners.forEach((listener) => {\r\n try {\r\n listener();\r\n } catch (error) {\r\n console.error(\"Error in voice start listener:\", error);\r\n }\r\n });\r\n }\r\n\r\n private emitVoiceStop(): void {\r\n this.voiceStopListeners.forEach((listener) => {\r\n try {\r\n listener();\r\n } catch (error) {\r\n console.error(\"Error in voice stop listener:\", error);\r\n }\r\n });\r\n }\r\n}\r\n","// Public callback/type aliases kept for backward compatibility with STTLogic API\r\nexport type WordUpdateCallback = (words: string[]) => void;\r\nexport type MicTimeUpdateCallback = (ms: number) => void;\r\nexport type RestartMetricsCallback = (count: number, lastDuration: number | null) => void;\r\nexport type VadCallbacks = { onSpeechStart?: () => void; onSpeechEnd?: () => void };\r\n\r\ntype LogCallback = (message: string, type?: \"info\" | \"error\" | \"warning\") => void;\r\ntype TranscriptCallback = (transcript: string) => void;\r\n\r\ninterface SpeechRecognitionEvent extends Event {\r\n results: SpeechRecognitionResultList;\r\n resultIndex: number;\r\n}\r\n\r\ninterface SpeechRecognitionErrorEvent extends Event {\r\n error: string;\r\n}\r\n\r\nexport interface ResetSTTOptions {\r\n sessionDurationMs?: number;\r\n interimSaveIntervalMs?: number;\r\n preserveTranscriptOnStart?: boolean;\r\n}\r\n\r\n// Alias to match previous public surface\r\nexport type STTLogicOptions = ResetSTTOptions;\r\n\r\nexport class ResetSTTLogic {\r\n private recognition: any;\r\n private isListening: boolean = false;\r\n private fullTranscript: string = \"\";\r\n private heardWords: string[] = [];\r\n private onLog: LogCallback;\r\n private onTranscript: TranscriptCallback;\r\n private onWordsUpdate: WordUpdateCallback | null = null;\r\n private onMicTimeUpdate: MicTimeUpdateCallback | null = null;\r\n private onRestartMetrics: RestartMetricsCallback | null = null;\r\n private options: Required<ResetSTTOptions>;\r\n\r\n private micOnTime: number = 0;\r\n private sessionDuration: number = 30000;\r\n private lastTickTime: number = 0;\r\n private micTimeInterval: number | null = null;\r\n private restartCount: number = 0;\r\n private isRestarting: boolean = false;\r\n private isRecognitionRunning: boolean = false;\r\n private lastInterimTranscript: string = \"\";\r\n private lastInterimSaveTime: number = 0;\r\n private interimSaveInterval: number = 1000;\r\n private lastInterimResultTime: number = 0;\r\n private lastSavedLength: number = 0;\r\n private transcriptBeforeRestart: string = \"\";\r\n private sessionStartTranscript: string = \"\";\r\n private resultHandler?: (e: Event) => void;\r\n private errorHandler?: (e: Event) => void;\r\n private endHandler?: (e?: Event) => void;\r\n private startHandler?: (e?: Event) => void;\r\n private sessionId: number = 0;\r\n private awaitingRestartFirstResultId: number | null = null;\r\n private lastWasFinal: boolean = false;\r\n private restartMetrics: Record<\r\n number,\r\n {\r\n requestedAt: number;\r\n stopAt?: number;\r\n startAttemptAt?: number;\r\n startedAt?: number;\r\n firstResultAt?: number;\r\n }\r\n > = {};\r\n private isAutoRestarting: boolean = false;\r\n private onUserSpeechStart?: () => void;\r\n private onUserSpeechEnd?: () => void;\r\n\r\n constructor(\r\n onLog: LogCallback,\r\n onTranscript: TranscriptCallback,\r\n options: ResetSTTOptions = {}\r\n ) {\r\n this.onLog = onLog;\r\n this.onTranscript = onTranscript;\r\n this.options = {\r\n sessionDurationMs: options.sessionDurationMs ?? 30000,\r\n interimSaveIntervalMs: options.interimSaveIntervalMs ?? 5000,\r\n preserveTranscriptOnStart: options.preserveTranscriptOnStart ?? false,\r\n };\r\n this.sessionDuration = this.options.sessionDurationMs;\r\n this.interimSaveInterval = this.options.interimSaveIntervalMs;\r\n\r\n const SpeechRecognitionAPI =\r\n (window as any).SpeechRecognition ||\r\n (window as any).webkitSpeechRecognition;\r\n\r\n if (!SpeechRecognitionAPI) {\r\n this.onLog(\"Speech Recognition API not supported\", \"error\");\r\n throw new Error(\"Speech Recognition API not available\");\r\n }\r\n\r\n this.recognition = new SpeechRecognitionAPI();\r\n this.setupRecognition();\r\n }\r\n\r\n public setWordsUpdateCallback(callback: WordUpdateCallback): void {\r\n this.onWordsUpdate = callback;\r\n }\r\n\r\n public setMicTimeUpdateCallback(callback: MicTimeUpdateCallback): void {\r\n this.onMicTimeUpdate = callback;\r\n }\r\n\r\n public setRestartMetricsCallback(\r\n callback: RestartMetricsCallback\r\n ): void {\r\n this.onRestartMetrics = callback;\r\n }\r\n\r\n public setVadCallbacks(\r\n onSpeechStart?: () => void,\r\n onSpeechEnd?: () => void\r\n ): void {\r\n this.onUserSpeechStart = onSpeechStart || undefined;\r\n this.onUserSpeechEnd = onSpeechEnd || undefined;\r\n }\r\n\r\n public getSessionDurationMs(): number {\r\n return this.sessionDuration;\r\n }\r\n\r\n public isInAutoRestart(): boolean {\r\n return this.isAutoRestarting;\r\n }\r\n\r\n public getFullTranscript(): string {\r\n if (this.transcriptBeforeRestart.length > 0) {\r\n if (this.fullTranscript.length > 0) {\r\n return (\r\n this.transcriptBeforeRestart +\r\n \" \" +\r\n this.fullTranscript\r\n ).trim();\r\n }\r\n return this.transcriptBeforeRestart;\r\n }\r\n return this.fullTranscript;\r\n }\r\n\r\n public clearTranscript(): void {\r\n this.fullTranscript = \"\";\r\n this.transcriptBeforeRestart = \"\";\r\n this.sessionStartTranscript = \"\";\r\n this.heardWords = [];\r\n }\r\n\r\n private setupRecognition(): void {\r\n this.recognition.lang = \"en-US\";\r\n this.recognition.interimResults = true;\r\n this.recognition.continuous = true;\r\n (this.recognition as any).maxAlternatives = 1;\r\n\r\n this.resultHandler = (event: Event) => {\r\n const speechEvent = event as SpeechRecognitionEvent;\r\n let completeTranscript = \"\";\r\n for (let i = 0; i < speechEvent.results.length; i++) {\r\n completeTranscript += speechEvent.results[i][0].transcript + \" \";\r\n }\r\n completeTranscript = completeTranscript.trim();\r\n\r\n const isFinal =\r\n speechEvent.results[speechEvent.results.length - 1].isFinal;\r\n\r\n completeTranscript = this.collapseRepeats(completeTranscript);\r\n this.lastInterimTranscript = completeTranscript;\r\n this.lastInterimResultTime = Date.now();\r\n\r\n if (this.awaitingRestartFirstResultId != null) {\r\n const rid = this.awaitingRestartFirstResultId;\r\n if (\r\n this.restartMetrics[rid] &&\r\n !this.restartMetrics[rid].firstResultAt\r\n ) {\r\n this.restartMetrics[rid].firstResultAt = Date.now();\r\n const delta =\r\n this.restartMetrics[rid].firstResultAt -\r\n this.restartMetrics[rid].requestedAt;\r\n this.onLog(\r\n `🔔 First result after restart #${rid} in ${delta}ms`,\r\n \"info\"\r\n );\r\n this.awaitingRestartFirstResultId = null;\r\n }\r\n }\r\n this.onLog(\r\n `[${isFinal ? \"FINAL\" : \"INTERIM\"}] \"${completeTranscript}\"`,\r\n isFinal ? \"info\" : \"warning\"\r\n );\r\n\r\n if (!isFinal && this.lastWasFinal) {\r\n try { this.onUserSpeechStart?.(); } catch {}\r\n }\r\n\r\n this.lastWasFinal = isFinal;\r\n\r\n if (isFinal) {\r\n this.fullTranscript = (this.sessionStartTranscript + \" \" + completeTranscript).trim();\r\n this.fullTranscript = this.collapseRepeats(this.fullTranscript);\r\n \r\n this.heardWords = this.fullTranscript\r\n .split(/\\s+/)\r\n .filter((word) => word.length > 0);\r\n \r\n this.onTranscript(this.getFullTranscript());\r\n this.lastSavedLength = this.fullTranscript.length;\r\n if (this.onWordsUpdate) this.onWordsUpdate(this.heardWords);\r\n \r\n this.lastInterimTranscript = \"\";\r\n \r\n if (this.awaitingRestartFirstResultId != null) {\r\n const rid = this.awaitingRestartFirstResultId;\r\n if (\r\n this.restartMetrics[rid] &&\r\n !this.restartMetrics[rid].firstResultAt\r\n ) {\r\n this.restartMetrics[rid].firstResultAt = Date.now();\r\n const startedAt =\r\n this.restartMetrics[rid].startedAt ||\r\n this.restartMetrics[rid].startAttemptAt ||\r\n Date.now();\r\n const firstResultDelta =\r\n this.restartMetrics[rid].firstResultAt -\r\n this.restartMetrics[rid].requestedAt;\r\n this.onLog(\r\n `🔔 First result after restart #${rid} in ${firstResultDelta}ms`,\r\n \"info\"\r\n );\r\n this.awaitingRestartFirstResultId = null;\r\n }\r\n }\r\n }\r\n };\r\n this.recognition.addEventListener(\"result\", this.resultHandler);\r\n\r\n this.errorHandler = (event: Event) => {\r\n const errorEvent = event as SpeechRecognitionErrorEvent;\r\n if (errorEvent.error === \"aborted\" && this.isRestarting) {\r\n this.onLog(\"Aborted during restart (ignored)\", \"info\");\r\n this.isRecognitionRunning = false;\r\n return;\r\n }\r\n this.onLog(`Error: ${errorEvent.error}`, \"error\");\r\n if (\r\n errorEvent.error === \"no-speech\" ||\r\n errorEvent.error === \"audio-capture\" ||\r\n errorEvent.error === \"network\"\r\n ) {\r\n setTimeout(() => {\r\n if (\r\n this.isListening &&\r\n !this.isRestarting &&\r\n !this.isRecognitionRunning\r\n ) {\r\n try {\r\n this.recognition.start();\r\n this.isRecognitionRunning = true;\r\n this.sessionId++;\r\n } catch (e) {\r\n this.onLog(`Failed restart after error: ${e}`, \"error\");\r\n }\r\n }\r\n }, 500);\r\n } else {\r\n this.onLog(\r\n `Unhandled SpeechRecognition error: ${errorEvent.error}`,\r\n \"warning\"\r\n );\r\n }\r\n };\r\n this.recognition.addEventListener(\"error\", this.errorHandler);\r\n\r\n this.endHandler = () => {\r\n this.isRecognitionRunning = false;\r\n if (this.isListening && !this.isRestarting) {\r\n setTimeout(() => {\r\n if (this.isListening && !this.isRestarting) {\r\n try {\r\n this.recognition.start();\r\n this.isRecognitionRunning = true;\r\n this.sessionId++;\r\n this.onLog(\r\n `🔁 Auto-resumed recognition after end (session ${this.sessionId})`,\r\n \"info\"\r\n );\r\n } catch (e) {\r\n this.onLog(`Failed to auto-start after end: ${e}`, \"error\");\r\n }\r\n }\r\n }, 100);\r\n }\r\n };\r\n this.recognition.addEventListener(\"end\", this.endHandler);\r\n\r\n this.startHandler = () => {\r\n this.isRecognitionRunning = true;\r\n const rid = this.awaitingRestartFirstResultId;\r\n if (rid != null && this.restartMetrics[rid]) {\r\n if (!this.restartMetrics[rid].startedAt) {\r\n this.restartMetrics[rid].startedAt = Date.now();\r\n this.onLog(\r\n `▶️ Restart #${rid} recognition started in ${\r\n this.restartMetrics[rid].startedAt -\r\n this.restartMetrics[rid].requestedAt\r\n }ms`,\r\n \"info\"\r\n );\r\n }\r\n }\r\n };\r\n this.recognition.addEventListener(\"start\", this.startHandler);\r\n }\r\n\r\n private waitForEventOnce(\r\n eventName: string,\r\n timeoutMs: number\r\n ): Promise<Event | null> {\r\n return new Promise((resolve) => {\r\n let timer: number | null = null;\r\n const handler = (ev: Event) => {\r\n if (timer !== null) clearTimeout(timer);\r\n this.recognition.removeEventListener(eventName, handler);\r\n resolve(ev);\r\n };\r\n this.recognition.addEventListener(eventName, handler);\r\n timer = window.setTimeout(() => {\r\n this.recognition.removeEventListener(eventName, handler);\r\n resolve(null);\r\n }, timeoutMs);\r\n });\r\n }\r\n\r\n private startMicTimer(): void {\r\n this.lastTickTime = Date.now();\r\n this.lastInterimSaveTime = Date.now();\r\n\r\n this.micTimeInterval = window.setInterval(() => {\r\n if (this.isListening) {\r\n const now = Date.now();\r\n const elapsed = now - this.lastTickTime;\r\n this.micOnTime += elapsed;\r\n this.lastTickTime = now;\r\n\r\n if (now - this.lastInterimSaveTime >= this.interimSaveInterval) {\r\n this.saveInterimToFinal();\r\n this.lastInterimSaveTime = now;\r\n }\r\n\r\n if (this.micOnTime >= this.sessionDuration) {\r\n if (!this.isRestarting) this.performRestart();\r\n }\r\n if (this.onMicTimeUpdate) this.onMicTimeUpdate(this.micOnTime);\r\n }\r\n }, 100);\r\n }\r\n\r\n private stopMicTimer(): void {\r\n if (this.micTimeInterval) {\r\n clearInterval(this.micTimeInterval);\r\n this.micTimeInterval = null;\r\n }\r\n }\r\n\r\n private saveInterimToFinal(): void {\r\n if (!this.lastInterimTranscript) return;\r\n const now = Date.now();\r\n if (now - this.lastInterimResultTime > this.interimSaveInterval && this.lastInterimTranscript.length > this.lastSavedLength) {\r\n this.fullTranscript = (this.fullTranscript + \" \" + this.lastInterimTranscript).trim();\r\n this.fullTranscript = this.collapseRepeats(this.fullTranscript);\r\n this.lastSavedLength = this.fullTranscript.length;\r\n if (this.onWordsUpdate) {\r\n const words = this.fullTranscript.split(/\\s+/).filter(w => w.length > 0);\r\n this.onWordsUpdate(words);\r\n }\r\n this.onTranscript(this.getFullTranscript());\r\n }\r\n }\r\n\r\n private getSuffixToAppend(base: string, current: string): string {\r\n if (!base || base.length === 0) return current;\r\n if (!current || current.length === 0) return \"\";\r\n base = base.trim();\r\n current = current.trim();\r\n if (current.startsWith(base)) {\r\n return current.slice(base.length).trim();\r\n }\r\n const maxOverlap = Math.min(base.length, current.length);\r\n for (let overlap = maxOverlap; overlap > 0; overlap--) {\r\n if (base.endsWith(current.slice(0, overlap))) {\r\n return current.slice(overlap).trim();\r\n }\r\n }\r\n return current;\r\n }\r\n\r\n private collapseRepeats(text: string): string {\r\n if (!text || text.trim().length === 0) return text.trim();\r\n let normalized = text.replace(/\\s+/g, \" \").trim();\r\n const n = normalized.length;\r\n const lps: number[] = new Array(n).fill(0);\r\n for (let i = 1; i < n; i++) {\r\n let j = lps[i - 1];\r\n while (j > 0 && normalized[i] !== normalized[j]) j = lps[j - 1];\r\n if (normalized[i] === normalized[j]) j++;\r\n lps[i] = j;\r\n }\r\n const period = n - lps[n - 1];\r\n if (period < n && n % period === 0) {\r\n return normalized.slice(0, period).trim();\r\n }\r\n const words = normalized.split(\" \");\r\n for (\r\n let block = Math.min(20, Math.floor(words.length / 2));\r\n block >= 1;\r\n block--\r\n ) {\r\n let i = 0;\r\n while (i + 2 * block <= words.length) {\r\n let blockA = words.slice(i, i + block).join(\" \");\r\n let blockB = words.slice(i + block, i + 2 * block).join(\" \");\r\n if (blockA === blockB) {\r\n words.splice(i + block, block);\r\n } else {\r\n i++;\r\n }\r\n }\r\n }\r\n const collapsedWords: string[] = [];\r\n for (const w of words) {\r\n if (\r\n collapsedWords.length === 0 ||\r\n collapsedWords[collapsedWords.length - 1] !== w\r\n )\r\n collapsedWords.push(w);\r\n }\r\n return collapsedWords.join(\" \").trim();\r\n }\r\n\r\n private performRestart(): void {\r\n if (!this.isListening || this.isRestarting) return;\r\n\r\n const restartStartTime = Date.now();\r\n this.restartCount++;\r\n this.isRestarting = true;\r\n this.isAutoRestarting = true;\r\n const rid = ++this.sessionId;\r\n this.awaitingRestartFirstResultId = rid;\r\n this.restartMetrics[rid] = { requestedAt: restartStartTime };\r\n\r\n this.onLog(\r\n `🔄 [AUTO-RESTART] Session ${rid} - buffering transcript, waiting for silence...`,\r\n \"warning\"\r\n );\r\n\r\n if (this.lastInterimTranscript.trim().length > 0) {\r\n this.saveInterimToFinal();\r\n }\r\n\r\n this.transcriptBeforeRestart = this.getFullTranscript();\r\n this.fullTranscript = \"\";\r\n this.sessionStartTranscript = \"\";\r\n this.lastInterimTranscript = \"\";\r\n this.heardWords = [];\r\n\r\n this.stopMicTimer();\r\n\r\n const stopTimeout = 600;\r\n const startTimeout = 1000;\r\n const firstResultTimeout = 2000;\r\n\r\n const stopNow = async () => {\r\n try {\r\n if (this.isRecognitionRunning) {\r\n this.recognition.stop();\r\n } else {\r\n this.onLog(\"Recognition not running at stop attempt\", \"warning\");\r\n }\r\n } catch (err) {\r\n this.onLog(`Stop threw: ${err}`, \"warning\");\r\n }\r\n const endEvent = await this.waitForEventOnce(\"end\", stopTimeout);\r\n if (!endEvent) {\r\n try {\r\n (this.recognition as any).abort();\r\n } catch (err) {\r\n this.onLog(`Abort also failed: ${err}`, \"error\");\r\n }\r\n await this.waitForEventOnce(\"end\", 300);\r\n }\r\n this.restartMetrics[rid].stopAt = Date.now();\r\n };\r\n\r\n (async () => {\r\n await stopNow();\r\n this.restartMetrics[rid].startAttemptAt = Date.now();\r\n try {\r\n if (!this.isRecognitionRunning) {\r\n this.sessionId = rid;\r\n this.recognition.start();\r\n } else {\r\n this.onLog(\r\n \"Recognition already running at restart time; skipping start.\",\r\n \"warning\"\r\n );\r\n }\r\n } catch (e) {\r\n this.onLog(`Failed to start recognition after restart: ${e}`, \"error\");\r\n }\r\n\r\n const startEv = await this.waitForEventOnce(\"start\", startTimeout);\r\n if (startEv) {\r\n this.restartMetrics[rid].startedAt = Date.now();\r\n } else {\r\n this.onLog(\r\n `Restart #${rid} did not produce start event within ${startTimeout}ms`,\r\n \"warning\"\r\n );\r\n }\r\n\r\n const resEv = await this.waitForEventOnce(\"result\", firstResultTimeout);\r\n if (resEv) {\r\n if (this.restartMetrics[rid])\r\n this.restartMetrics[rid].firstResultAt = Date.now();\r\n const firstResultDelta =\r\n (this.restartMetrics[rid].firstResultAt || Date.now()) -\r\n (this.restartMetrics[rid].requestedAt || Date.now());\r\n this.onLog(\r\n `🔔 First result after restart #${rid} in ${firstResultDelta}ms`,\r\n \"info\"\r\n );\r\n } else {\r\n this.onLog(\r\n `Restart #${rid} produced no result within ${firstResultTimeout}ms`,\r\n \"warning\"\r\n );\r\n }\r\n\r\n const startedAt =\r\n this.restartMetrics[rid].startedAt ||\r\n this.restartMetrics[rid].startAttemptAt ||\r\n Date.now();\r\n const restartDuration = startedAt - this.restartMetrics[rid].requestedAt;\r\n if (this.onRestartMetrics)\r\n this.onRestartMetrics(this.restartCount, restartDuration);\r\n this.onLog(\r\n `✅ Session ${rid} restarted in ${restartDuration}ms - resuming from silence gate`,\r\n \"info\"\r\n );\r\n this.startMicTimer();\r\n this.isRestarting = false;\r\n this.isAutoRestarting = false;\r\n })();\r\n }\r\n\r\n public start(): void {\r\n if (this.isListening) return;\r\n\r\n try {\r\n this.isListening = true;\r\n if (!this.options.preserveTranscriptOnStart) {\r\n this.fullTranscript = \"\";\r\n this.heardWords = [];\r\n this.transcriptBeforeRestart = \"\";\r\n this.sessionStartTranscript = \"\";\r\n } else {\r\n this.sessionStartTranscript = this.fullTranscript;\r\n }\r\n \r\n this.micOnTime = 0;\r\n this.restartCount = 0;\r\n this.lastSavedLength = 0;\r\n this.lastInterimTranscript = \"\";\r\n this.lastWasFinal = false;\r\n\r\n if (!this.isRecognitionRunning) {\r\n this.sessionId++;\r\n this.recognition.start();\r\n this.isRecognitionRunning = true;\r\n }\r\n this.startMicTimer();\r\n this.onLog(\r\n \"Listening started (auto-restart every 30s of mic time)\",\r\n \"info\"\r\n );\r\n } catch (error) {\r\n this.isListening = false;\r\n this.onLog(`Failed to start: ${error}`, \"error\");\r\n }\r\n }\r\n\r\n public stop(): void {\r\n if (!this.isListening) return;\r\n\r\n try {\r\n this.isListening = false;\r\n this.isAutoRestarting = false;\r\n this.stopMicTimer();\r\n this.recognition.stop();\r\n this.isRecognitionRunning = false;\r\n this.onLog(\r\n `Stopped listening (total mic time: ${(this.micOnTime / 1000).toFixed(\r\n 1\r\n )}s, restarts: ${this.restartCount})`,\r\n \"info\"\r\n );\r\n } catch (error) {\r\n this.onLog(`Failed to stop: ${error}`, \"error\");\r\n }\r\n }\r\n\r\n public destroy(): void {\r\n this.isListening = false;\r\n this.stopMicTimer();\r\n try {\r\n (this.recognition as any).abort?.();\r\n } catch (e) {}\r\n try {\r\n if (this.resultHandler)\r\n this.recognition.removeEventListener(\"result\", this.resultHandler);\r\n if (this.errorHandler)\r\n this.recognition.removeEventListener(\"error\", this.errorHandler);\r\n if (this.endHandler)\r\n this.recognition.removeEventListener(\r\n \"end\",\r\n this.endHandler as EventListener\r\n );\r\n if (this.startHandler)\r\n this.recognition.removeEventListener(\r\n \"start\",\r\n this.startHandler as EventListener\r\n );\r\n } catch (e) {\r\n }\r\n }\r\n}\r\n\r\n// Backward-compatible alias so consumers can import STTLogic as before\r\nexport class STTLogic extends ResetSTTLogic {}\r\n","export interface PiperVoiceConfig {\r\n voiceId: string;\r\n modelPath?: string;\r\n sampleRate?: number;\r\n lengthScale?: number;\r\n noiseScale?: number;\r\n speaker?: string;\r\n}\r\n\r\nexport interface PreparedPiperVoice {\r\n voiceId: string;\r\n modelPath: string;\r\n sampleRate: number;\r\n inference: {\r\n lengthScale: number;\r\n noiseScale: number;\r\n };\r\n metadata: Record<string, unknown>;\r\n}\r\n\r\n/**\r\n * Normalize Piper voice configuration so downstream synthesis gets predictable defaults.\r\n */\r\nexport function preparePiperVoice(config: PiperVoiceConfig): PreparedPiperVoice {\r\n const modelPath = config.modelPath ?? `voices/${config.voiceId}.onnx`;\r\n\r\n return {\r\n voiceId: config.voiceId,\r\n modelPath,\r\n sampleRate: config.sampleRate ?? 22050,\r\n inference: {\r\n lengthScale: config.lengthScale ?? 1.0,\r\n noiseScale: config.noiseScale ?? 0.667,\r\n },\r\n metadata: {\r\n speaker: config.speaker ?? \"default\",\r\n },\r\n };\r\n}\r\n","export interface StreamTokensOptions {\r\n chunkSize?: number;\r\n delayMs?: number;\r\n onChunk?: (text: string) => Promise<void> | void;\r\n}\r\n\r\nexport interface StreamTokensResult {\r\n chunksEmitted: number;\r\n characters: number;\r\n}\r\n\r\nfunction isAsyncIterable<T>(value: AsyncIterable<T> | Iterable<T>): value is AsyncIterable<T> {\r\n return typeof (value as AsyncIterable<T>)[Symbol.asyncIterator] === \"function\";\r\n}\r\n\r\nconst sleep = (ms: number) => new Promise((resolve) => setTimeout(resolve, ms));\r\n\r\n/**\r\n * Convert incremental tokens to speech-sized chunks. Consumers can bridge this into an audio renderer.\r\n */\r\nexport async function streamTokensToSpeech(\r\n tokens: AsyncIterable<string> | Iterable<string>,\r\n options: StreamTokensOptions = {},\r\n): Promise<StreamTokensResult> {\r\n const chunkSize = options.chunkSize ?? 40;\r\n const delayMs = options.delayMs ?? 0;\r\n\r\n let buffer = \"\";\r\n let chunksEmitted = 0;\r\n let characters = 0;\r\n\r\n const emit = async () => {\r\n if (!buffer) return;\r\n characters += buffer.length;\r\n chunksEmitted += 1;\r\n if (options.onChunk) {\r\n await options.onChunk(buffer);\r\n }\r\n buffer = \"\";\r\n if (delayMs > 0) {\r\n await sleep(delayMs);\r\n }\r\n };\r\n\r\n if (isAsyncIterable(tokens)) {\r\n for await (const token of tokens) {\r\n buffer += token;\r\n if (buffer.length >= chunkSize) {\r\n await emit();\r\n }\r\n }\r\n } else {\r\n for (const token of tokens) {\r\n buffer += token;\r\n if (buffer.length >= chunkSize) {\r\n await emit();\r\n }\r\n }\r\n }\r\n\r\n if (buffer) {\r\n await emit();\r\n }\r\n\r\n return { chunksEmitted, characters };\r\n}\r\n","export type OrtDevice = \"cpu\" | \"webgpu\";\r\nexport type OrtLogLevel = \"verbose\" | \"warning\" | \"error\";\r\n\r\nexport interface OrtEnvironmentConfig {\r\n device?: OrtDevice;\r\n logLevel?: OrtLogLevel;\r\n providers?: string[];\r\n}\r\n\r\nexport interface OrtEnvironment {\r\n device: OrtDevice;\r\n logLevel: OrtLogLevel;\r\n providers: string[];\r\n initialized: boolean;\r\n init: () => Promise<void>;\r\n}\r\n\r\n/**\r\n * Minimal Onnx Runtime bootstrapper. This is intentionally dependency-light: callers can pass\r\n * a custom provider list when integrating with onnxruntime-web or node-ort.\r\n */\r\nexport async function createOrtEnvironment(\r\n config: OrtEnvironmentConfig = {},\r\n): Promise<OrtEnvironment> {\r\n const providers = config.providers ?? (config.device === \"webgpu\" ? [\"webgpu\", \"wasm\"] : [\"wasm\"]);\r\n\r\n const environment: OrtEnvironment = {\r\n device: config.device ?? \"cpu\",\r\n logLevel: config.logLevel ?? \"warning\",\r\n providers,\r\n initialized: false,\r\n async init() {\r\n // Real implementation would call into the ORT API. Here we just flip a flag for consumers.\r\n this.initialized = true;\r\n },\r\n };\r\n\r\n await environment.init();\r\n return environment;\r\n}\r\n","import { createOrtEnvironment, OrtEnvironment, OrtEnvironmentConfig } from \"./ort-setup.js\";\r\nimport { preparePiperVoice, PiperVoiceConfig, PreparedPiperVoice } from \"./prepare-piper-voice.js\";\r\n\r\nexport type SynthResult = string | ArrayBuffer | Uint8Array;\r\nexport type Synthesizer = (text: string, voice: PreparedPiperVoice) => Promise<SynthResult>;\r\nexport type Player = (audio: SynthResult) => Promise<void>;\r\n\r\nconst voiceCache = new Map<string, PreparedPiperVoice>();\r\nlet ortEnv: OrtEnvironment | null = null;\r\n\r\nexport async function ensureOrtReady(config: OrtEnvironmentConfig = {}): Promise<OrtEnvironment> {\r\n if (ortEnv) return ortEnv;\r\n ortEnv = await createOrtEnvironment(config);\r\n return ortEnv;\r\n}\r\n\r\nexport async function ensureVoiceLoaded(config: PiperVoiceConfig): Promise<PreparedPiperVoice> {\r\n const cached = voiceCache.get(config.voiceId);\r\n if (cached) return cached;\r\n const voice = preparePiperVoice(config);\r\n voiceCache.set(config.voiceId, voice);\r\n return voice;\r\n}\r\n\r\nexport async function warmupPiper(\r\n voiceConfig: PiperVoiceConfig,\r\n synth: Synthesizer,\r\n text = \"warmup\",\r\n): Promise<void> {\r\n const voice = await ensureVoiceLoaded(voiceConfig);\r\n await synth(text, voice);\r\n}\r\n\r\nexport function resetVoiceCache(): void {\r\n voiceCache.clear();\r\n}\r\n\r\nexport function getBackendLabel(device: string | undefined): string {\r\n if (!device) return \"auto\";\r\n return device === \"webgpu\" ? \"WebGPU\" : \"CPU\";\r\n}\r\n\r\nexport function isCorruptModelError(error: unknown): boolean {\r\n if (!error) return false;\r\n const msg = typeof error === \"string\" ? error : (error as { message?: string }).message;\r\n if (!msg) return false;\r\n return /corrupt|checksum|integrity/i.test(msg);\r\n}\r\n\r\n// ---------------------------------------------------------------------------\r\n// Workers and helpers\r\n// ---------------------------------------------------------------------------\r\n\r\nexport async function* synthesizerWorker(\r\n textQueue: AsyncIterable<string>,\r\n voiceConfig: PiperVoiceConfig,\r\n synth: Synthesizer,\r\n): AsyncGenerator<SynthResult, void, unknown> {\r\n const voice = await ensureVoiceLoaded(voiceConfig);\r\n for await (const text of textQueue) {\r\n yield synth(text, voice);\r\n }\r\n}\r\n\r\nexport async function playerWorker(\r\n audioQueue: AsyncIterable<SynthResult>,\r\n play: Player,\r\n): Promise<void> {\r\n for await (const audio of audioQueue) {\r\n await play(audio);\r\n }\r\n}\r\n\r\nexport function nextBoundaryIndex(text: string): number {\r\n const idx = text.search(/[.!?,]/);\r\n return idx >= 0 ? idx : -1;\r\n}\r\n\r\nexport function emitSentence(queue: SimpleQueue<string>, sentence: string): void {\r\n const trimmed = sentence.trim();\r\n if (trimmed) {\r\n queue.put(trimmed);\r\n }\r\n}\r\n\r\nexport function handleChunk(state: { buffer: string }, chunk: string, queue: SimpleQueue<string>): void {\r\n state.buffer += chunk;\r\n let boundary = nextBoundaryIndex(state.buffer);\r\n while (boundary >= 0) {\r\n const sentence = state.buffer.slice(0, boundary + 1);\r\n state.buffer = state.buffer.slice(boundary + 1);\r\n emitSentence(queue, sentence);\r\n boundary = nextBoundaryIndex(state.buffer);\r\n }\r\n}\r\n\r\nexport function getAsyncIterator<T>(\r\n source: AsyncIterable<T> | Iterable<T>,\r\n): AsyncIterable<T> {\r\n if ((source as AsyncIterable<T>)[Symbol.asyncIterator]) {\r\n return source as AsyncIterable<T>;\r\n }\r\n return {\r\n async *[Symbol.asyncIterator]() {\r\n for (const item of source as Iterable<T>) {\r\n yield item;\r\n }\r\n },\r\n };\r\n}\r\n\r\nexport class SimpleQueue<T> implements AsyncIterable<T> {\r\n private buffer: T[] = [];\r\n private resolvers: Array<(value: IteratorResult<T>) => void> = [];\r\n\r\n put(item: T): void {\r\n if (this.resolvers.length > 0) {\r\n const resolve = this.resolvers.shift();\r\n resolve?.({ value: item, done: false });\r\n } else {\r\n this.buffer.push(item);\r\n }\r\n }\r\n\r\n size(): number {\r\n return this.buffer.length;\r\n }\r\n\r\n async get(): Promise<T> {\r\n if (this.buffer.length > 0) {\r\n return this.buffer.shift() as T;\r\n }\r\n return new Promise<T>((resolve) => {\r\n this.resolvers.push(({ value }) => resolve(value as T));\r\n });\r\n }\r\n\r\n async *[Symbol.asyncIterator](): AsyncIterator<T> {\r\n while (true) {\r\n const value = await this.get();\r\n yield value;\r\n }\r\n }\r\n}\r\n","import { streamTokensToSpeech } from \"./stream-tokens-to-speech.js\";\r\nimport {\r\n ensureOrtReady,\r\n ensureVoiceLoaded,\r\n handleChunk,\r\n SimpleQueue,\r\n synthesizerWorker,\r\n playerWorker,\r\n getAsyncIterator,\r\n emitSentence,\r\n} from \"./piper.js\";\r\nimport type { PiperVoiceConfig, PreparedPiperVoice } from \"./prepare-piper-voice.js\";\r\nimport type { OrtEnvironmentConfig } from \"./ort-setup.js\";\r\nimport type { SynthResult, Synthesizer, Player } from \"./piper.js\";\r\n\r\nexport interface StreamingTTSOptions {\r\n voice: PiperVoiceConfig;\r\n ort?: OrtEnvironmentConfig;\r\n synth?: Synthesizer;\r\n play?: Player;\r\n chunkSize?: number;\r\n delayMs?: number;\r\n}\r\n\r\nexport interface StreamingTTSController {\r\n ensureReady(): Promise<void>;\r\n addChunk(text: string): Promise<void>;\r\n finishStreaming(): Promise<void>;\r\n stop(): void;\r\n synthAndPlayChunk(text: string): Promise<void>;\r\n processQueue(): Promise<void>;\r\n createTokenIterable(text: string): Iterable<string>;\r\n}\r\n\r\nconst defaultSynth: Synthesizer = async (text) => text;\r\nconst defaultPlayer: Player = async () => undefined;\r\n\r\nexport function useStreamingTTS(options: StreamingTTSOptions): StreamingTTSController {\r\n const textQueue = new SimpleQueue<string>();\r\n const audioQueue = new SimpleQueue<SynthResult>();\r\n const bufferState = { buffer: \"\" };\r\n\r\n let ready = false;\r\n let stopped = false;\r\n let voice: PreparedPiperVoice | null = null;\r\n\r\n const synth = options.synth ?? defaultSynth;\r\n const play = options.play ?? defaultPlayer;\r\n const chunkSize = options.chunkSize ?? 48;\r\n const delayMs = options.delayMs ?? 0;\r\n\r\n async function ensureReady(): Promise<void> {\r\n if (ready) return;\r\n await ensureOrtReady(options.ort ?? {});\r\n voice = await ensureVoiceLoaded(options.voice);\r\n ready = true;\r\n }\r\n\r\n async function addChunk(text: string): Promise<void> {\r\n handleChunk(bufferState, text, textQueue);\r\n if (bufferState.buffer.length >= chunkSize) {\r\n emitSentence(textQueue, bufferState.buffer);\r\n bufferState.buffer = \"\";\r\n }\r\n }\r\n\r\n async function finishStreaming(): Promise<void> {\r\n if (bufferState.buffer) {\r\n emitSentence(textQueue, bufferState.buffer);\r\n bufferState.buffer = \"\";\r\n }\r\n }\r\n\r\n function stop(): void {\r\n stopped = true;\r\n }\r\n\r\n async function synthAndPlayChunk(text: string): Promise<void> {\r\n await ensureReady();\r\n const audio = await synth(text, voice as PreparedPiperVoice);\r\n await play(audio);\r\n }\r\n\r\n async function processQueue(): Promise<void> {\r\n await ensureReady();\r\n const tokenIterator = getAsyncIterator(textQueue as AsyncIterable<string>);\r\n const audioIterator = synthesizerWorker(tokenIterator, options.voice, synth);\r\n await playerWorker(audioIterator, play);\r\n }\r\n\r\n function createTokenIterable(text: string): Iterable<string> {\r\n return text.split(/\\s+/g).filter(Boolean);\r\n }\r\n\r\n async function streamTokens(tokens: AsyncIterable<string> | Iterable<string>): Promise<void> {\r\n await ensureReady();\r\n await streamTokensToSpeech(tokens, {\r\n chunkSize,\r\n delayMs,\r\n onChunk: async (chunk) => {\r\n if (stopped) return;\r\n await synthAndPlayChunk(chunk);\r\n },\r\n });\r\n }\r\n\r\n // Kick off background processors\r\n processQueue().catch(() => undefined);\r\n streamTokens(textQueue as AsyncIterable<string>).catch(() => undefined);\r\n\r\n return {\r\n ensureReady,\r\n addChunk,\r\n finishStreaming,\r\n stop,\r\n synthAndPlayChunk,\r\n processQueue,\r\n createTokenIterable,\r\n };\r\n}\r\n","/**\r\n * Piper TTS Synthesizer using @realtimex/piper-tts-web\r\n * This library handles text-to-phoneme conversion properly using espeak-ng\r\n *\r\n * Note: @realtimex/piper-tts-web handles ONNX Runtime configuration internally,\r\n * so NO separate ort-setup.js is needed!\r\n */\r\n\r\nimport * as piperTts from \"@realtimex/piper-tts-web\";\r\n\r\nexport interface PiperSynthesizerConfig {\r\n /** Voice ID (e.g., \"en_US-hfc_female-medium\") */\r\n voiceId?: string;\r\n /** Sample rate (default: 22050) */\r\n sampleRate?: number;\r\n}\r\n\r\nexport interface SynthesisResult {\r\n /** Audio data as WAV Blob */\r\n audioBlob: Blob;\r\n /** Audio data as Float32Array (for direct playback) */\r\n audio: Float32Array;\r\n /** Sample rate */\r\n sampleRate: number;\r\n /** Duration in seconds */\r\n duration: number;\r\n}\r\n\r\nconst DEFAULT_VOICE_ID = \"en_US-hfc_female-medium\";\r\n\r\n/**\r\n * Piper TTS Synthesizer\r\n * Uses @mintplex-labs/piper-tts-web for proper text-to-speech conversion\r\n */\r\nexport class TTSLogic {\r\n private config: PiperSynthesizerConfig;\r\n private ready = false;\r\n private voiceLoaded = false;\r\n\r\n constructor(config: PiperSynthesizerConfig = {}) {\r\n this.config = {\r\n voiceId: DEFAULT_VOICE_ID,\r\n sampleRate: 22050,\r\n ...config,\r\n };\r\n }\r\n\r\n /**\r\n * Initialize the synthesizer by loading the voice model\r\n */\r\n async initialize(): Promise<void> {\r\n if (this.ready) return;\r\n\r\n try {\r\n const voiceId = this.config.voiceId!;\r\n console.log(\"📍 Loading Piper voice:\", voiceId);\r\n\r\n // Check if voice is already cached\r\n const storedVoices = await piperTts.stored();\r\n const alreadyCached = Array.isArray(storedVoices)\r\n ? storedVoices.includes(voiceId)\r\n : false;\r\n\r\n if (!alreadyCached) {\r\n console.log(\"⬇️ Downloading voice model...\");\r\n await piperTts.download(voiceId, (progress) => {\r\n if (progress?.total) {\r\n const pct = Math.round((progress.loaded * 100) / progress.total);\r\n console.log(`⬇️ Downloading: ${pct}%`);\r\n }\r\n });\r\n } else {\r\n console.log(\"✓ Voice found in cache\");\r\n }\r\n\r\n this.voiceLoaded = true;\r\n this.ready = true;\r\n console.log(\"✓ Piper synthesizer initialized\");\r\n } catch (error) {\r\n throw new Error(`Failed to initialize Piper synthesizer: ${error}`);\r\n }\r\n }\r\n\r\n /**\r\n * Check if the synthesizer is ready\r\n */\r\n isReady(): boolean {\r\n return this.ready;\r\n }\r\n\r\n /**\r\n * Synthesize speech from text\r\n * @param text - Text to convert to speech\r\n * @returns Audio data as WAV Blob and Float32Array\r\n */\r\n async synthesize(text: string): Promise<SynthesisResult> {\r\n if (!this.ready) {\r\n throw new Error(\"Synthesizer not initialized. Call initialize() first.\");\r\n }\r\n\r\n const trimmed = text?.trim();\r\n if (!trimmed) {\r\n throw new Error(\"No text provided for synthesis\");\r\n }\r\n\r\n try {\r\n // Use piper-tts-web to convert text to speech\r\n // This handles text-to-phoneme conversion internally using espeak-ng\r\n const wavBlob: Blob = await piperTts.predict({\r\n text: trimmed,\r\n voiceId: this.config.voiceId!,\r\n });\r\n\r\n // Convert Blob to Float32Array for direct playback\r\n const arrayBuffer = await wavBlob.arrayBuffer();\r\n const audioContext = new (window.AudioContext ||\r\n (window as any).webkitAudioContext)();\r\n const decodedBuffer = await audioContext.decodeAudioData(arrayBuffer);\r\n const audioData = decodedBuffer.getChannelData(0);\r\n audioContext.close();\r\n\r\n return {\r\n audioBlob: wavBlob,\r\n audio: audioData,\r\n sampleRate: decodedBuffer.sampleRate,\r\n duration: decodedBuffer.duration,\r\n };\r\n } catch (error) {\r\n throw new Error(`Synthesis failed: ${error}`);\r\n }\r\n }\r\n\r\n /**\r\n * Synthesize and return WAV Blob only (faster, no decoding)\r\n */\r\n async synthesizeToBlob(text: string): Promise<Blob> {\r\n if (!this.ready) {\r\n throw new Error(\"Synthesizer not initialized. Call initialize() first.\");\r\n }\r\n\r\n const trimmed = text?.trim();\r\n if (!trimmed) {\r\n throw new Error(\"No text provided for synthesis\");\r\n }\r\n\r\n return piperTts.predict({\r\n text: trimmed,\r\n voiceId: this.config.voiceId!,\r\n });\r\n }\r\n\r\n /**\r\n * Stop current synthesis (not directly supported, but we can track state)\r\n */\r\n stop(): void {\r\n // Piper doesn't have a stop method, but we track state\r\n console.log(\"Stop requested\");\r\n }\r\n\r\n /**\r\n * Dispose of the synthesizer and free resources\r\n */\r\n async dispose(): Promise<void> {\r\n this.ready = false;\r\n this.voiceLoaded = false;\r\n }\r\n}\r\n\r\n/**\r\n * Create and initialize a Piper synthesizer\r\n */\r\n// export async function createPiperSynthesizer(\r\n// config: PiperSynthesizerConfig = {}\r\n// ): Promise<PiperSynthesizer> {\r\n// const synthesizer = new PiperSynthesizer(config);\r\n// await synthesizer.initialize();\r\n// return synthesizer;\r\n// }\r\n\r\n/**\r\n * @deprecated Use PiperSynthesizer.synthesize() which handles text-to-phoneme internally\r\n * This is kept for backwards compatibility but should not be used directly\r\n */\r\nexport function textToPhonemes(_text: string): number[] {\r\n console.warn(\r\n \"textToPhonemes is deprecated. Use PiperSynthesizer.synthesize(text) instead.\"\r\n );\r\n return [];\r\n}\r\n","/**\r\n * Web Audio API Player\r\n * Plays synthesized audio using the Web Audio API\r\n */\r\n\r\nexport interface AudioPlayerConfig {\r\n sampleRate?: number;\r\n volume?: number;\r\n}\r\n\r\n/**\r\n * Audio Player for Web Audio API\r\n */\r\nexport class AudioPlayer {\r\n private audioContext: AudioContext | null = null;\r\n private config: AudioPlayerConfig;\r\n private currentSource: AudioBufferSourceNode | null = null;\r\n\r\n constructor(config: AudioPlayerConfig = {}) {\r\n this.config = {\r\n sampleRate: 22050,\r\n volume: 1.0,\r\n ...config,\r\n };\r\n }\r\n\r\n /**\r\n * Initialize the audio context\r\n */\r\n private getAudioContext(): AudioContext {\r\n if (!this.audioContext) {\r\n this.audioContext = new (window.AudioContext || (window as any).webkitAudioContext)({\r\n sampleRate: this.config.sampleRate,\r\n });\r\n }\r\n return this.audioContext;\r\n }\r\n\r\n /**\r\n * Play audio data\r\n * @param audioData - Float32Array of audio samples\r\n * @param sampleRate - Sample rate of the audio\r\n */\r\n async play(audioData: Float32Array, sampleRate: number): Promise<void> {\r\n const ctx = this.getAudioContext();\r\n\r\n // Resume audio context if suspended (browser security requirement)\r\n if (ctx.state === 'suspended') {\r\n await ctx.resume();\r\n }\r\n\r\n // Create audio buffer\r\n const audioBuffer = ctx.createBuffer(1, audioData.length, sampleRate);\r\n audioBuffer.getChannelData(0).set(audioData);\r\n\r\n // Create source\r\n const source = ctx.createBufferSource();\r\n source.buffer = audioBuffer;\r\n\r\n // Create gain node for volume control\r\n const gainNode = ctx.createGain();\r\n gainNode.gain.value = this.config.volume!;\r\n\r\n // Connect nodes\r\n source.connect(gainNode);\r\n gainNode.connect(ctx.destination);\r\n\r\n // Store current source\r\n this.currentSource = source;\r\n\r\n // Play\r\n source.start(0);\r\n\r\n // Wait for playback to finish\r\n return new Promise<void>((resolve) => {\r\n source.onended = () => {\r\n this.currentSource = null;\r\n resolve();\r\n };\r\n });\r\n }\r\n\r\n /**\r\n * Stop current playback\r\n */\r\n stop(): void {\r\n if (this.currentSource) {\r\n try {\r\n this.currentSource.stop();\r\n this.currentSource = null;\r\n } catch (error) {\r\n // Ignore errors if already stopped\r\n }\r\n }\r\n }\r\n\r\n /**\r\n * Set volume (0.0 to 1.0)\r\n */\r\n setVolume(volume: number): void {\r\n this.config.volume = Math.max(0, Math.min(1, volume));\r\n }\r\n\r\n /**\r\n * Close the audio context and free resources\r\n */\r\n async close(): Promise<void> {\r\n this.stop();\r\n if (this.audioContext) {\r\n await this.audioContext.close();\r\n this.audioContext = null;\r\n }\r\n }\r\n}\r\n\r\n/**\r\n * Create and return an audio player instance\r\n */\r\nexport function createAudioPlayer(config?: AudioPlayerConfig): AudioPlayer {\r\n return new AudioPlayer(config);\r\n}\r\n"]}
|