Spaces:
Running
Running
Create presentation-agent.html
Browse files- static/presentation-agent.html +301 -0
static/presentation-agent.html
ADDED
@@ -0,0 +1,301 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<!DOCTYPE html>
|
2 |
+
<html lang="en">
|
3 |
+
<head>
|
4 |
+
<meta charset="UTF-8">
|
5 |
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
6 |
+
<title>Presentation Chatbot</title>
|
7 |
+
<link href="https://cdn.jsdelivr.net/npm/[email protected]/dist/css/bootstrap.min.css" rel="stylesheet">
|
8 |
+
<link href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.0.0-beta3/css/all.min.css" rel="stylesheet">
|
9 |
+
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.global.prod.js"></script>
|
10 |
+
<script src="https://cdn.jsdelivr.net/npm/marked/marked.min.js"></script>
|
11 |
+
<style>
|
12 |
+
:root {
|
13 |
+
--primary-color: #007bff;
|
14 |
+
--secondary-color: #6c757d;
|
15 |
+
--background-color: #ffffff;
|
16 |
+
--text-color: #333333;
|
17 |
+
--message-bg-user: #e9ecef;
|
18 |
+
--message-bg-bot: #f8f9fa;
|
19 |
+
--input-bg: #ffffff;
|
20 |
+
--border-color: #dee2e6;
|
21 |
+
--scrollbar-thumb: #adb5bd;
|
22 |
+
--scrollbar-track: #f1f3f5;
|
23 |
+
}
|
24 |
+
|
25 |
+
body.dark-mode {
|
26 |
+
--primary-color: #4da3ff;
|
27 |
+
--secondary-color: #a1a8ae;
|
28 |
+
--background-color: #1a1a1a;
|
29 |
+
--text-color: #ffffff;
|
30 |
+
--message-bg-user: #2c2c2c;
|
31 |
+
--message-bg-bot: #383838;
|
32 |
+
--input-bg: #2c2c2c;
|
33 |
+
--border-color: #4a4a4a;
|
34 |
+
--scrollbar-thumb: #4a4a4a;
|
35 |
+
--scrollbar-track: #2c2c2c;
|
36 |
+
}
|
37 |
+
|
38 |
+
body {
|
39 |
+
background-color: var(--background-color);
|
40 |
+
color: var(--text-color);
|
41 |
+
transition: background-color 0.3s, color 0.3s;
|
42 |
+
}
|
43 |
+
|
44 |
+
html, body, #app {
|
45 |
+
height: 100%;
|
46 |
+
}
|
47 |
+
|
48 |
+
.chat-outer-container {
|
49 |
+
max-width: 800px;
|
50 |
+
height: 100vh;
|
51 |
+
margin: 0 auto;
|
52 |
+
display: flex;
|
53 |
+
flex-direction: column;
|
54 |
+
}
|
55 |
+
|
56 |
+
.chat-container {
|
57 |
+
flex-grow: 1;
|
58 |
+
overflow-y: auto;
|
59 |
+
padding: 1rem;
|
60 |
+
scrollbar-width: thin;
|
61 |
+
scrollbar-color: var(--scrollbar-thumb) var(--scrollbar-track);
|
62 |
+
}
|
63 |
+
|
64 |
+
.chat-container::-webkit-scrollbar {
|
65 |
+
width: 8px;
|
66 |
+
}
|
67 |
+
|
68 |
+
.chat-container::-webkit-scrollbar-track {
|
69 |
+
background: var(--scrollbar-track);
|
70 |
+
}
|
71 |
+
|
72 |
+
.chat-container::-webkit-scrollbar-thumb {
|
73 |
+
background-color: var(--scrollbar-thumb);
|
74 |
+
border-radius: 4px;
|
75 |
+
border: 2px solid var(--scrollbar-track);
|
76 |
+
}
|
77 |
+
|
78 |
+
.message {
|
79 |
+
padding: 0.75rem;
|
80 |
+
margin-bottom: 1rem;
|
81 |
+
border-radius: 15px;
|
82 |
+
}
|
83 |
+
|
84 |
+
.user-message {
|
85 |
+
background-color: var(--message-bg-user);
|
86 |
+
border-radius: 15px 15px 0 15px;
|
87 |
+
}
|
88 |
+
|
89 |
+
.bot-message {
|
90 |
+
background-color: var(--message-bg-bot);
|
91 |
+
border-radius: 15px 15px 15px 0;
|
92 |
+
}
|
93 |
+
|
94 |
+
.loading-spinner {
|
95 |
+
width: 3rem;
|
96 |
+
height: 3rem;
|
97 |
+
color: var(--primary-color);
|
98 |
+
}
|
99 |
+
|
100 |
+
.presentation-iframe {
|
101 |
+
width: 100%;
|
102 |
+
height: 60vh;
|
103 |
+
border: none;
|
104 |
+
}
|
105 |
+
|
106 |
+
.input-container {
|
107 |
+
padding: 1rem;
|
108 |
+
background-color: var(--input-bg);
|
109 |
+
border-top: 1px solid var(--border-color);
|
110 |
+
position: relative;
|
111 |
+
}
|
112 |
+
|
113 |
+
.reset-button {
|
114 |
+
position: absolute;
|
115 |
+
top: -40px;
|
116 |
+
right: 10px;
|
117 |
+
background-color: var(--secondary-color);
|
118 |
+
color: var(--background-color);
|
119 |
+
border: none;
|
120 |
+
border-radius: 50%;
|
121 |
+
width: 36px;
|
122 |
+
height: 36px;
|
123 |
+
display: flex;
|
124 |
+
align-items: center;
|
125 |
+
justify-content: center;
|
126 |
+
cursor: pointer;
|
127 |
+
transition: background-color 0.3s;
|
128 |
+
}
|
129 |
+
|
130 |
+
.reset-button:hover {
|
131 |
+
background-color: var(--primary-color);
|
132 |
+
}
|
133 |
+
|
134 |
+
.mode-toggle {
|
135 |
+
position: fixed;
|
136 |
+
top: 10px;
|
137 |
+
right: 10px;
|
138 |
+
background: none;
|
139 |
+
border: none;
|
140 |
+
color: var(--text-color);
|
141 |
+
font-size: 1.5rem;
|
142 |
+
cursor: pointer;
|
143 |
+
z-index: 1000;
|
144 |
+
}
|
145 |
+
|
146 |
+
input[type="text"] {
|
147 |
+
background-color: var(--input-bg);
|
148 |
+
color: var(--text-color);
|
149 |
+
border: 1px solid var(--border-color);
|
150 |
+
}
|
151 |
+
|
152 |
+
input[type="text"]::placeholder {
|
153 |
+
color: var(--secondary-color);
|
154 |
+
}
|
155 |
+
|
156 |
+
.btn-primary {
|
157 |
+
background-color: var(--primary-color);
|
158 |
+
border-color: var(--primary-color);
|
159 |
+
}
|
160 |
+
|
161 |
+
.btn-primary:hover {
|
162 |
+
background-color: var(--secondary-color);
|
163 |
+
border-color: var(--secondary-color);
|
164 |
+
}
|
165 |
+
</style>
|
166 |
+
</head>
|
167 |
+
<body>
|
168 |
+
<div id="app">
|
169 |
+
<button @click="toggleDarkMode" class="mode-toggle" :title="isDarkMode ? 'Switch to Light Mode' : 'Switch to Dark Mode'">
|
170 |
+
<i :class="isDarkMode ? 'fas fa-sun' : 'fas fa-moon'"></i>
|
171 |
+
</button>
|
172 |
+
<div class="chat-outer-container">
|
173 |
+
<div class="chat-container">
|
174 |
+
<h1 class="text-center mb-4">Presentation Chatbot</h1>
|
175 |
+
<div v-for="(message, index) in chatHistory" :key="index" class="message" :class="message.type === 'user' ? 'user-message' : 'bot-message'">
|
176 |
+
<div v-if="message.type === 'bot'" v-html="message.content"></div>
|
177 |
+
<div v-else>{{ message.content }}</div>
|
178 |
+
<iframe v-if="message.html" :srcdoc="message.html" class="presentation-iframe mt-2"></iframe>
|
179 |
+
</div>
|
180 |
+
<div v-if="isLoading" class="text-center">
|
181 |
+
<div class="spinner-border loading-spinner" role="status">
|
182 |
+
<span class="visually-hidden">Loading...</span>
|
183 |
+
</div>
|
184 |
+
</div>
|
185 |
+
</div>
|
186 |
+
<div class="alert alert-danger" v-if="errorMessage">{{ errorMessage }}</div>
|
187 |
+
<div class="input-container">
|
188 |
+
<form @submit.prevent="sendMessage" class="d-flex">
|
189 |
+
<input v-model="userInput" type="text" class="form-control me-2" placeholder="Type your message...">
|
190 |
+
<button type="submit" class="btn btn-primary" :disabled="isLoading">Send</button>
|
191 |
+
</form>
|
192 |
+
<button @click="resetConversation" class="reset-button" title="Reset Conversation">
|
193 |
+
<i class="fas fa-redo"></i>
|
194 |
+
</button>
|
195 |
+
</div>
|
196 |
+
</div>
|
197 |
+
</div>
|
198 |
+
|
199 |
+
<script>
|
200 |
+
const { createApp } = Vue;
|
201 |
+
|
202 |
+
createApp({
|
203 |
+
data() {
|
204 |
+
return {
|
205 |
+
userInput: '',
|
206 |
+
chatHistory: [],
|
207 |
+
conversationId: '',
|
208 |
+
isLoading: false,
|
209 |
+
errorMessage: '',
|
210 |
+
AUTH_TOKEN: "44d5c2ac18ced6fc25c1e57dcd06fc0b31fb4ad97bf56e67540671a647465df4",
|
211 |
+
modelId: 'openai/gpt-4o-mini',
|
212 |
+
isDarkMode: false
|
213 |
+
}
|
214 |
+
},
|
215 |
+
mounted() {
|
216 |
+
this.resetConversation();
|
217 |
+
this.isDarkMode = window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches;
|
218 |
+
this.applyDarkMode();
|
219 |
+
},
|
220 |
+
updated() {
|
221 |
+
this.scrollToBottom();
|
222 |
+
},
|
223 |
+
methods: {
|
224 |
+
async sendMessage() {
|
225 |
+
if (!this.userInput.trim()) return;
|
226 |
+
|
227 |
+
this.chatHistory.push({ type: 'user', content: this.userInput });
|
228 |
+
const userMessage = this.userInput;
|
229 |
+
this.userInput = '';
|
230 |
+
this.isLoading = true;
|
231 |
+
this.errorMessage = '';
|
232 |
+
|
233 |
+
const payload = {
|
234 |
+
prompt: userMessage,
|
235 |
+
model_id: this.modelId,
|
236 |
+
conversation_id: this.conversationId,
|
237 |
+
user_id: "web_user"
|
238 |
+
};
|
239 |
+
|
240 |
+
try {
|
241 |
+
const response = await fetch('https://pvanand-audio-chat.hf.space/presentation-agent', {
|
242 |
+
method: 'POST',
|
243 |
+
headers: {
|
244 |
+
'accept': 'application/json',
|
245 |
+
'X-API-Key': this.AUTH_TOKEN,
|
246 |
+
'Content-Type': 'application/json'
|
247 |
+
},
|
248 |
+
body: JSON.stringify(payload)
|
249 |
+
});
|
250 |
+
|
251 |
+
if (!response.ok) {
|
252 |
+
const errorText = await response.text();
|
253 |
+
throw new Error(`HTTP error! status: ${response.status}, message: ${errorText}`);
|
254 |
+
}
|
255 |
+
|
256 |
+
const data = await response.json();
|
257 |
+
const botMessage = {
|
258 |
+
type: 'bot',
|
259 |
+
content: data.response ? marked.parse(data.response) : '',
|
260 |
+
html: data.html_presentation || null
|
261 |
+
};
|
262 |
+
this.chatHistory.push(botMessage);
|
263 |
+
} catch (error) {
|
264 |
+
this.errorMessage = `Error: ${error.message}`;
|
265 |
+
setTimeout(() => {
|
266 |
+
this.errorMessage = '';
|
267 |
+
}, 5000);
|
268 |
+
} finally {
|
269 |
+
this.isLoading = false;
|
270 |
+
}
|
271 |
+
},
|
272 |
+
resetConversation() {
|
273 |
+
this.chatHistory = [];
|
274 |
+
this.conversationId = this.generateUUID();
|
275 |
+
this.errorMessage = '';
|
276 |
+
},
|
277 |
+
generateUUID() {
|
278 |
+
return Math.random().toString(36).substring(2, 15) + Math.random().toString(36).substring(2, 15);
|
279 |
+
},
|
280 |
+
scrollToBottom() {
|
281 |
+
this.$nextTick(() => {
|
282 |
+
const container = this.$el.querySelector('.chat-container');
|
283 |
+
container.scrollTop = container.scrollHeight;
|
284 |
+
});
|
285 |
+
},
|
286 |
+
toggleDarkMode() {
|
287 |
+
this.isDarkMode = !this.isDarkMode;
|
288 |
+
this.applyDarkMode();
|
289 |
+
},
|
290 |
+
applyDarkMode() {
|
291 |
+
if (this.isDarkMode) {
|
292 |
+
document.body.classList.add('dark-mode');
|
293 |
+
} else {
|
294 |
+
document.body.classList.remove('dark-mode');
|
295 |
+
}
|
296 |
+
}
|
297 |
+
}
|
298 |
+
}).mount('#app');
|
299 |
+
</script>
|
300 |
+
</body>
|
301 |
+
</html>
|