forked from i-am-alice/3rd-devs
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
27 changed files
with
2,716 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
<!DOCTYPE html> | ||
<html lang="en" class="dark"> | ||
<head> | ||
<meta charset="UTF-8"> | ||
<meta name="viewport" content="width=device-width, initial-scale=1.0"> | ||
<meta http-equiv="X-UA-Compatible" content="ie=edge"> | ||
<title>Agent Call</title> | ||
|
||
<script src="https://cdn.tailwindcss.com"></script> | ||
<script src="https://cdn.jsdelivr.net/npm/d3@7"></script> | ||
<script src="https://cdn.jsdelivr.net/npm/markmap-view"></script> | ||
</head> | ||
<body class="bg-gradient-to-br from-gray-900 to-gray-800 min-h-screen flex items-center justify-center"> | ||
<div class="bg-gray-800/50 backdrop-blur-xl p-8 rounded-2xl shadow-2xl w-full max-w-[25%] text-center border border-gray-700/50"> | ||
|
||
<!-- Canvas for the pulsing circle --> | ||
<canvas id="visualizationCanvas" width="384" height="200" class="mx-auto"></canvas> | ||
|
||
<!-- Conversation History --> | ||
<div id="conversationHistory" class="w-full h-64 overflow-y-auto mb-4 p-4 bg-gray-900/50 rounded-xl text-left text-gray-100 scrollbar-thin scrollbar-thumb-gray-600 scrollbar-track-gray-800"> | ||
<!-- Conversation messages will appear here --> | ||
</div> | ||
|
||
<!-- Latest Transcription --> | ||
<div id="latestTranscription" class="block w-full p-4 mb-4 bg-gray-900/50 rounded-xl text-left text-gray-300"> | ||
... | ||
</div> | ||
|
||
<!-- Call / Hang Up Button --> | ||
<button id="callBtn" class="w-full py-3 px-6 rounded-full transition duration-300 bg-gradient-to-r from-blue-500 to-indigo-600 text-white font-semibold shadow-lg hover:shadow-xl hover:from-blue-600 hover:to-indigo-700 focus:outline-none focus:ring-2 focus:ring-blue-400 focus:ring-opacity-50"> | ||
Call | ||
</button> | ||
</div> | ||
|
||
|
||
|
||
<!-- Markmap container --> | ||
<div id="markmapContainer" style="margin-left: 50px; width: 1080px; height: 1080px; background: #dcdcdc;" class="rounded-md"> | ||
<svg id="markmap" style="width: 100%; height: 100%;"></svg> | ||
</div> | ||
<script type="module" src="./src/app.ts"></script> | ||
</body> | ||
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,88 @@ | ||
const BACKEND_URL = 'http://localhost:3000'; // Update if necessary | ||
|
||
async function fetchAPI(endpoint: string, options: RequestInit): Promise<Response> { | ||
const response = await fetch(`${BACKEND_URL}/api/${endpoint}`, options); | ||
if (!response.ok) throw new Error(`API error: ${await response.text()}`); | ||
return response; | ||
} | ||
|
||
export async function transcribe(audioBlob: Blob): Promise<string> { | ||
const formData = new FormData(); | ||
formData.append('file', audioBlob, 'audio.wav'); | ||
formData.append('model', 'whisper-1'); | ||
|
||
try { | ||
const response = await fetchAPI('transcribe', { method: 'POST', body: formData }); | ||
const { transcription } = await response.json(); | ||
console.log('Transcription received from API:', transcription); | ||
return transcription; | ||
} catch (error) { | ||
console.error('Whisper API error:', error); | ||
throw error; | ||
} | ||
} | ||
|
||
let currentAudio: HTMLAudioElement | null = null; | ||
|
||
export async function speak(text: string): Promise<HTMLAudioElement> { | ||
try { | ||
const response = await fetchAPI('speakEleven', { | ||
method: 'POST', | ||
headers: { 'Content-Type': 'application/json' }, | ||
body: JSON.stringify({ text }), | ||
}); | ||
|
||
const audioBlob = await response.blob(); | ||
const audioUrl = URL.createObjectURL(audioBlob); | ||
currentAudio = new Audio(audioUrl); | ||
currentAudio.play(); | ||
return currentAudio; | ||
} catch (error) { | ||
console.error('Speak function error:', error); | ||
throw error; | ||
} | ||
} | ||
|
||
export function stopSpeaking(): void { | ||
if (currentAudio) { | ||
currentAudio.pause(); | ||
currentAudio.currentTime = 0; | ||
currentAudio = null; | ||
} | ||
} | ||
|
||
interface Message { | ||
role: 'user' | 'assistant' | 'system'; | ||
content: string; | ||
} | ||
|
||
export async function chat(messages: Message[]): Promise<{ message: string, markmapSyntax: string }> { | ||
const response = await fetchAPI('chat', { | ||
method: 'POST', | ||
headers: { 'Content-Type': 'application/json' }, | ||
body: JSON.stringify({ messages }), | ||
}); | ||
|
||
const data = await response.json(); | ||
return { | ||
message: data.choices[0].message.content, | ||
markmapSyntax: data.markmapSyntax, | ||
}; | ||
} | ||
|
||
export async function transcribeAudioBlob(audioBlob: Blob): Promise<string> { | ||
const formData = new FormData(); | ||
formData.append('file', audioBlob, 'audio.wav'); | ||
|
||
const response = await fetch('/api/transcribe', { | ||
method: 'POST', | ||
body: formData, | ||
}); | ||
|
||
if (!response.ok) { | ||
throw new Error('Transcription failed'); | ||
} | ||
|
||
const data = await response.json(); | ||
return data.transcription; | ||
} |
Oops, something went wrong.