webapp/components/call-interface.tsx (84 lines of code) (raw):
"use client";
import React, { useState, useEffect } from "react";
import TopBar from "@/components/top-bar";
import ChecklistAndConfig from "@/components/checklist-and-config";
import SessionConfigurationPanel from "@/components/session-configuration-panel";
import Transcript from "@/components/transcript";
import FunctionCallsPanel from "@/components/function-calls-panel";
import { Item } from "@/components/types";
import handleRealtimeEvent from "@/lib/handle-realtime-event";
import PhoneNumberChecklist from "@/components/phone-number-checklist";
const CallInterface = () => {
const [selectedPhoneNumber, setSelectedPhoneNumber] = useState("");
const [allConfigsReady, setAllConfigsReady] = useState(false);
const [items, setItems] = useState<Item[]>([]);
const [callStatus, setCallStatus] = useState("disconnected");
const [ws, setWs] = useState<WebSocket | null>(null);
useEffect(() => {
if (allConfigsReady && !ws) {
const newWs = new WebSocket("ws://localhost:8081/logs");
newWs.onopen = () => {
console.log("Connected to logs websocket");
setCallStatus("connected");
};
newWs.onmessage = (event) => {
const data = JSON.parse(event.data);
console.log("Received logs event:", data);
handleRealtimeEvent(data, setItems);
};
newWs.onclose = () => {
console.log("Logs websocket disconnected");
setWs(null);
setCallStatus("disconnected");
};
setWs(newWs);
}
}, [allConfigsReady, ws]);
return (
<div className="h-screen bg-white flex flex-col">
<ChecklistAndConfig
ready={allConfigsReady}
setReady={setAllConfigsReady}
selectedPhoneNumber={selectedPhoneNumber}
setSelectedPhoneNumber={setSelectedPhoneNumber}
/>
<TopBar />
<div className="flex-grow p-4 h-full overflow-hidden flex flex-col">
<div className="grid grid-cols-12 gap-4 h-full">
{/* Left Column */}
<div className="col-span-3 flex flex-col h-full overflow-hidden">
<SessionConfigurationPanel
callStatus={callStatus}
onSave={(config) => {
if (ws && ws.readyState === WebSocket.OPEN) {
const updateEvent = {
type: "session.update",
session: {
...config,
},
};
console.log("Sending update event:", updateEvent);
ws.send(JSON.stringify(updateEvent));
}
}}
/>
</div>
{/* Middle Column: Transcript */}
<div className="col-span-6 flex flex-col gap-4 h-full overflow-hidden">
<PhoneNumberChecklist
selectedPhoneNumber={selectedPhoneNumber}
allConfigsReady={allConfigsReady}
setAllConfigsReady={setAllConfigsReady}
/>
<Transcript items={items} />
</div>
{/* Right Column: Function Calls */}
<div className="col-span-3 flex flex-col h-full overflow-hidden">
<FunctionCallsPanel items={items} ws={ws} />
</div>
</div>
</div>
</div>
);
};
export default CallInterface;