diff --git a/components/app.tsx b/components/app.tsx index 725170b2..1e76c88e 100644 --- a/components/app.tsx +++ b/components/app.tsx @@ -1,9 +1,15 @@ 'use client'; -import { useEffect, useMemo, useState } from 'react'; +import { useCallback, useEffect, useMemo, useState } from 'react'; import { Room, RoomEvent } from 'livekit-client'; import { motion } from 'motion/react'; -import { RoomAudioRenderer, RoomContext, StartAudio } from '@livekit/components-react'; +import { + LiveKitRoom, + RoomAudioRenderer, + RoomContext, + StartAudio, + useRoomConnection, +} from '@livekit/components-react'; import { toastAlert } from '@/components/alert-toast'; import { SessionView } from '@/components/session-view'; import { Toaster } from '@/components/ui/sonner'; @@ -19,58 +25,25 @@ interface AppProps { } export function App({ appConfig }: AppProps) { - const room = useMemo(() => new Room(), []); const [sessionStarted, setSessionStarted] = useState(false); const { connectionDetails, refreshConnectionDetails } = useConnectionDetails(); - useEffect(() => { - const onDisconnected = () => { - setSessionStarted(false); - refreshConnectionDetails(); - }; - const onMediaDevicesError = (error: Error) => { - toastAlert({ - title: 'Encountered an error with your media devices', - description: `${error.name}: ${error.message}`, - }); - }; - room.on(RoomEvent.MediaDevicesError, onMediaDevicesError); - room.on(RoomEvent.Disconnected, onDisconnected); - return () => { - room.off(RoomEvent.Disconnected, onDisconnected); - room.off(RoomEvent.MediaDevicesError, onMediaDevicesError); - }; - }, [room, refreshConnectionDetails]); + const enableMicrophonePreConnectBuffer = useCallback(async (room: Room) => { + room.localParticipant.setMicrophoneEnabled(true, undefined, { + preConnectBuffer: appConfig.isPreConnectBufferEnabled, + }); + }, []); - useEffect(() => { - let aborted = false; - if (sessionStarted && room.state === 'disconnected' && connectionDetails) { - Promise.all([ - room.localParticipant.setMicrophoneEnabled(true, undefined, { - preConnectBuffer: appConfig.isPreConnectBufferEnabled, - }), - room.connect(connectionDetails.serverUrl, connectionDetails.participantToken), - ]).catch((error) => { - if (aborted) { - // Once the effect has cleaned up after itself, drop any errors - // - // These errors are likely caused by this effect rerunning rapidly, - // resulting in a previous run `disconnect` running in parallel with - // a current run `connect` - return; - } - - toastAlert({ - title: 'There was an error connecting to the agent', - description: `${error.name}: ${error.message}`, - }); - }); - } - return () => { - aborted = true; - room.disconnect(); - }; - }, [room, sessionStarted, connectionDetails, appConfig.isPreConnectBufferEnabled]); + const onDisconnected = useCallback(() => { + setSessionStarted(false); + refreshConnectionDetails(); + }, [refreshConnectionDetails]); + const onMediaDeviceFailure = useCallback((error: Error) => { + toastAlert({ + title: 'Encountered an error with your media devices', + description: `${error.name}: ${error.message}`, + }); + }, []); const { startButtonText } = appConfig; @@ -86,7 +59,14 @@ export function App({ appConfig }: AppProps) { transition={{ duration: 0.5, ease: 'linear', delay: sessionStarted ? 0 : 0.5 }} /> - + {/* --- */} @@ -103,7 +83,7 @@ export function App({ appConfig }: AppProps) { delay: sessionStarted ? 0.5 : 0, }} /> - +