237 lines
7.4 KiB
HTML
237 lines
7.4 KiB
HTML
<!DOCTYPE html>
|
|
<html lang="zh-CN">
|
|
<head>
|
|
<meta charset="UTF-8">
|
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
<title>CardioAI - 心血管健康语音助手</title>
|
|
<style>
|
|
body {
|
|
font-family: Arial, sans-serif;
|
|
background-color: #f5f5f5;
|
|
margin: 0;
|
|
padding: 20px;
|
|
}
|
|
.container {
|
|
max-width: 800px;
|
|
margin: 0 auto;
|
|
background-color: white;
|
|
padding: 40px;
|
|
border-radius: 10px;
|
|
box-shadow: 0 0 10px rgba(0,0,0,0.1);
|
|
}
|
|
h1 {
|
|
color: #333;
|
|
text-align: center;
|
|
margin-bottom: 40px;
|
|
}
|
|
.input-section {
|
|
margin-bottom: 30px;
|
|
}
|
|
label {
|
|
display: block;
|
|
margin-bottom: 10px;
|
|
font-weight: bold;
|
|
color: #555;
|
|
}
|
|
textarea {
|
|
width: 100%;
|
|
padding: 15px;
|
|
border: 1px solid #ddd;
|
|
border-radius: 5px;
|
|
font-size: 16px;
|
|
resize: vertical;
|
|
min-height: 100px;
|
|
}
|
|
button {
|
|
background-color: #4CAF50;
|
|
color: white;
|
|
padding: 15px 30px;
|
|
border: none;
|
|
border-radius: 5px;
|
|
font-size: 16px;
|
|
cursor: pointer;
|
|
width: 100%;
|
|
margin-top: 15px;
|
|
}
|
|
button:hover {
|
|
background-color: #45a049;
|
|
}
|
|
button:disabled {
|
|
background-color: #cccccc;
|
|
cursor: not-allowed;
|
|
}
|
|
.result {
|
|
margin-top: 40px;
|
|
padding: 25px;
|
|
background-color: #f9f9f9;
|
|
border-radius: 5px;
|
|
border-left: 4px solid #4CAF50;
|
|
}
|
|
.result h2 {
|
|
color: #333;
|
|
margin-top: 0;
|
|
margin-bottom: 20px;
|
|
}
|
|
.text-answer {
|
|
background-color: white;
|
|
padding: 20px;
|
|
border-radius: 5px;
|
|
border: 1px solid #ddd;
|
|
margin-bottom: 20px;
|
|
line-height: 1.6;
|
|
}
|
|
.audio-section {
|
|
margin-top: 20px;
|
|
}
|
|
audio {
|
|
width: 100%;
|
|
margin-top: 10px;
|
|
}
|
|
.error {
|
|
margin-top: 30px;
|
|
padding: 20px;
|
|
background-color: #ffebee;
|
|
border-radius: 5px;
|
|
border-left: 4px solid #f44336;
|
|
color: #c62828;
|
|
}
|
|
.loading {
|
|
display: inline-block;
|
|
width: 20px;
|
|
height: 20px;
|
|
border: 3px solid rgba(255,255,255,.3);
|
|
border-radius: 50%;
|
|
border-top-color: #fff;
|
|
animation: spin 1s ease-in-out infinite;
|
|
}
|
|
@keyframes spin {
|
|
to { transform: rotate(360deg); }
|
|
}
|
|
.button-text {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
gap: 10px;
|
|
}
|
|
@media (max-width: 768px) {
|
|
.container {
|
|
padding: 20px;
|
|
}
|
|
h1 {
|
|
font-size: 24px;
|
|
}
|
|
}
|
|
</style>
|
|
</head>
|
|
<body>
|
|
<div class="container">
|
|
<h1>CardioAI - 心血管健康语音助手</h1>
|
|
|
|
<div class="input-section">
|
|
<label for="question">请输入您的心血管健康问题</label>
|
|
<textarea id="question" placeholder="例如:如何预防心血管疾病?高血压患者的饮食建议有哪些?"></textarea>
|
|
<button id="submitBtn" onclick="askQuestion()">
|
|
<span class="button-text">
|
|
<span>提交问题</span>
|
|
<span id="loading" class="loading" style="display: none;"></span>
|
|
</span>
|
|
</button>
|
|
</div>
|
|
|
|
<div id="result" class="result" style="display: none;">
|
|
<h2>回答结果</h2>
|
|
<div class="text-answer" id="textAnswer"></div>
|
|
<div class="audio-section">
|
|
<label>语音回答</label>
|
|
<audio id="audioPlayer" controls autoplay>
|
|
您的浏览器不支持音频播放。
|
|
</audio>
|
|
</div>
|
|
</div>
|
|
|
|
<div id="error" class="error" style="display: none;">
|
|
<h2>错误</h2>
|
|
<p id="errorMessage"></p>
|
|
</div>
|
|
</div>
|
|
|
|
<script>
|
|
function askQuestion() {
|
|
const question = document.getElementById('question').value.trim();
|
|
const submitBtn = document.getElementById('submitBtn');
|
|
const loading = document.getElementById('loading');
|
|
const result = document.getElementById('result');
|
|
const error = document.getElementById('error');
|
|
const textAnswer = document.getElementById('textAnswer');
|
|
const audioPlayer = document.getElementById('audioPlayer');
|
|
|
|
if (!question) {
|
|
showError('请输入您的问题');
|
|
return;
|
|
}
|
|
|
|
// 显示加载状态
|
|
submitBtn.disabled = true;
|
|
loading.style.display = 'inline-block';
|
|
result.style.display = 'none';
|
|
error.style.display = 'none';
|
|
|
|
// 发送POST请求
|
|
fetch('/ask_cardio', {
|
|
method: 'POST',
|
|
headers: {
|
|
'Content-Type': 'application/json'
|
|
},
|
|
body: JSON.stringify({ question: question })
|
|
})
|
|
.then(response => response.json())
|
|
.then(data => {
|
|
if (data.error) {
|
|
showError(data.error);
|
|
} else {
|
|
// 显示文字回答
|
|
textAnswer.textContent = data.text_answer;
|
|
|
|
// 构造音频URL并设置到音频播放器
|
|
const audioUrl = `data:audio/mp3;base64,${data.audio_base64}`;
|
|
audioPlayer.src = audioUrl;
|
|
|
|
// 显示结果区域
|
|
result.style.display = 'block';
|
|
|
|
// 自动播放音频
|
|
audioPlayer.play().catch(e => {
|
|
console.error('音频播放失败:', e);
|
|
});
|
|
}
|
|
})
|
|
.catch(error => {
|
|
showError('请求过程中发生错误,请稍后重试');
|
|
console.error('Error:', error);
|
|
})
|
|
.finally(() => {
|
|
// 隐藏加载状态
|
|
submitBtn.disabled = false;
|
|
loading.style.display = 'none';
|
|
});
|
|
}
|
|
|
|
function showError(message) {
|
|
const error = document.getElementById('error');
|
|
const errorMessage = document.getElementById('errorMessage');
|
|
const result = document.getElementById('result');
|
|
|
|
errorMessage.textContent = message;
|
|
error.style.display = 'block';
|
|
result.style.display = 'none';
|
|
}
|
|
|
|
// 回车键提交
|
|
document.getElementById('question').addEventListener('keydown', function(e) {
|
|
if (e.key === 'Enter' && e.ctrlKey) {
|
|
askQuestion();
|
|
}
|
|
});
|
|
</script>
|
|
</body>
|
|
</html> |