Spaces:
Runtime error
Runtime error
<html> | |
<head> | |
<meta charset="utf-8"> | |
<meta name="viewport" content="width=device-width, initial-scale=1.0"> | |
<!--網頁圖示--> | |
<link rel="shortcut icon" href="{{ url_for('static', filename='favicon.ico') }}"> | |
<style> | |
/*載入字體*/ | |
@import url('https://fonts.googleapis.com/css2?family=Mochiy+Pop+One&family=Zen+Maru+Gothic:wght@500&display=swap'); | |
html{ | |
/*設定字體*/ | |
font-family: 'Mochiy Pop One', sans-serif; | |
font-family: 'Zen Maru Gothic', sans-serif; | |
/*設定邊界*/ | |
margin-top: 10px; | |
margin-left: 20px; | |
/*背景顏色*/ | |
background-color: #f9f7f0; | |
} | |
h1{ | |
/*設定字體大小*/ | |
font-size: 70px; | |
/*設定字和字之間的寬度*/ | |
letter-spacing:4px; | |
/*設定字的顏色*/ | |
color: #18b7be; | |
/*設定邊界*/ | |
margin-left: 70px; | |
} | |
.box1{ | |
/*設定為彈性盒子,元素從左到右橫向排列*/ | |
display:flex; | |
/*元素對齊方式*/ | |
justify-content: space-evenly; | |
} | |
.box2{ | |
/*設定為彈性盒子*/ | |
display:flex; | |
/*元素縱向排列*/ | |
flex-direction: column; | |
/*元素對齊方式*/ | |
justify-content: center; | |
align-items: center; | |
} | |
.box3{ | |
display: none; | |
} | |
.use{ | |
/*設定背景顏色*/ | |
background-color:white; | |
/*設定字體大小*/ | |
font-size: 30px; | |
/*設定字體顏色*/ | |
color: #072a40; | |
/*角角的弧度*/ | |
border-radius: 50px; | |
/*設定邊界*/ | |
padding:0 25px 0 0; | |
} | |
.record{ | |
/*設定為彈性盒子*/ | |
display: flex; | |
/*設定邊界*/ | |
margin-bottom: 30px; | |
} | |
button,input{ | |
/*設定字體*/ | |
font-family: 'Mochiy Pop One', sans-serif; | |
font-family: 'Zen Maru Gothic', sans-serif; | |
/*設定字體大小*/ | |
font-size: 25px; | |
/*設定按鈕的框框*/ | |
border:2px #178ca4 solid; | |
/*設定角角的弧度*/ | |
border-radius: 20px; | |
/*設定滑鼠樣式*/ | |
cursor: pointer; | |
/*設定長寬*/ | |
height: 50px; | |
width: 100px; | |
/*設定背景顏色*/ | |
background-color:#f9f7f0; | |
/*設定字體顏色*/ | |
color:#178ca4; | |
/*設定動畫時間*/ | |
transition-duration: 0.4s; | |
/*設定邊界*/ | |
margin: 10px; | |
} | |
/*滑鼠放到上面的樣式*/ | |
button:hover,input:hover{ | |
/*設定背景顏色*/ | |
background-color: #178ca4; | |
/*設定字的顏色*/ | |
color: #f9f7f0; | |
} | |
/*設定播放器的背景顏色*/ | |
audio::-webkit-media-controls-panel { | |
background-color: white; | |
} | |
/*設定表格樣式*/ | |
table{ | |
/*設為彈性盒子*/ | |
display: flexbox; | |
/*設定字的大小*/ | |
font-size: 20px; | |
/*設定寬度*/ | |
width:870px; | |
/*表格的寬度的決定方式*/ | |
table-layout: fixed; | |
/*設定字的顏色*/ | |
color: #f9f7f0; | |
} | |
@media screen and (max-width:1000px){ | |
h1{ | |
font-size: 25px; | |
letter-spacing:2px; | |
text-align: left; | |
padding-bottom: 0px; | |
} | |
li{ | |
font-size: 20px; | |
} | |
.box1{ | |
width: 100%; | |
} | |
.box2{ | |
display: none; | |
} | |
.box3{ | |
display: block; | |
width: 100%; | |
text-align: center; | |
} | |
} | |
.pronounce{ | |
font-size:20px; | |
/*設定字的大小*/ | |
background-color: #178ca4; | |
/*設定背景的顏色*/ | |
color: #f9f7f0; | |
/*設定字的顏色*/ | |
} | |
.pronounce:hover{ | |
background-color: black; | |
width: 100px; | |
/*設定背景的顏色*/ | |
} | |
tr{ | |
text-align: center; | |
} | |
</style> | |
<title>日語發音校正系統</title> | |
</head> | |
<body> | |
<div> | |
<h1>日語發音校正系統</h1> | |
</div> | |
<div class="box1"> | |
<div class="use"> | |
<ul style="list-style-type:none;"> | |
<!--使用說明--> | |
<li style="font-size: 35px;"><b>方法:</b></li> | |
<li>1. 允許麥克風的權限</li> | |
<li>2. 在右側的字表中選擇字詞</li> | |
<li>3. 按下字表上方的開始鍵</li> | |
<li>4. 對著裝置念出選擇的字詞</li> | |
<li>5. 按下完成鍵</li> | |
<li>6. 可於在播放器確認語音</li> | |
<li>7. 確認後按下上傳鍵</li> | |
<li>8. 等待系統的判定結果</li> | |
</ol> | |
</div> | |
<div class="box2"> | |
<!--放錄音、上傳、播放器--> | |
<div class="record"> | |
<!--錄音按鈕--> | |
<button class="record-btn" >開始</button> | |
<!--上傳按鈕--> | |
<form class="POST" enctype="multipart/form-data" action="{{ url_for('upload_file') }}"> | |
<input type="submit" value="上傳" name="audio" accept="audio/*"> | |
</form> | |
<!--播放器--> | |
<audio style="margin: 10px;height: 50px;width: 400px;" controls class="audio-player"></audio> | |
</div> | |
<!--字表--> | |
<table> | |
<colgroup> | |
<col span="1" style="background-color: #178ca4;"> | |
<col span="1" style="background-color: #18b7be;"> | |
<col span="1" style="background-color: #178ca4;"> | |
<col span="1" style="background-color: #18b7be;"> | |
<col span="1" style="background-color: #178ca4;"> | |
<col span="1" style="background-color: #18b7be;"> | |
</colgroup> | |
<caption style="color:#072a40;font-size: 40px;"><b>字表</b></caption> | |
<tr> | |
<th>日文</th> | |
<th>中文</th> | |
<th>日文</th> | |
<th>中文</th> | |
<th>日文</th> | |
<th>中文</th> | |
</tr> | |
<tr> | |
<td class="pronounce" data-audio="audio/1.mp3">わたし</td> | |
<td>我</td> | |
<td class="pronounce" data-audio="audio/2.mp3">わたしたち</td> | |
<td>我們</td> | |
<td class="pronounce" data-audio="audio/3.mp3">あなた</td> | |
<td>你</td> | |
</tr> | |
<tr> | |
<td class="pronounce" data-audio="audio/4.mp3">あのひと</td> | |
<td>那個人</td> | |
<td class="pronounce" data-audio="audio/5.mp3">あのかた</td> | |
<td>那個人-有禮貌</td> | |
<td class="pronounce" data-audio="audio/6.mp3">みなさん</td> | |
<td>大家</td> | |
</tr> | |
<tr> | |
<td class="pronounce" data-audio="audio/7.mp3">せんせい</td> | |
<td>老師</td> | |
<td class="pronounce" data-audio="audio/8.mp3">きょうし</td> | |
<td>教室</td> | |
<td class="pronounce" data-audio="audio/9.mp3">がくせい</td> | |
<td>學生</td> | |
</tr> | |
<tr> | |
<td class="pronounce" data-audio="audio/10.mp3">かいしゃいん</td> | |
<td>公司職員</td> | |
<td class="pronounce" data-audio="audio/11.mp3">しゃいん</td> | |
<td>職員</td> | |
<td class="pronounce" data-audio="audio/12.mp3">ぎんこういん</td> | |
<td>銀行員</td> | |
</tr> | |
<tr> | |
<td class="pronounce" data-audio="audio/13.mp3">いしゃ</td> | |
<td>醫生</td> | |
<td class="pronounce" data-audio="audio/14.mp3">けんきゅうしゃ</td> | |
<td>研究員</td> | |
<td class="pronounce" data-audio="audio/15.mp3">エンジニア</td> | |
<td>工程師</td> | |
</tr> | |
<tr> | |
<td class="pronounce" data-audio="audio/16.mp3">だいがく</td> | |
<td>大學</td> | |
<td class="pronounce" data-audio="audio/17.mp3">びょういん</td> | |
<td>醫院</td> | |
<td class="pronounce" data-audio="audio/18.mp3">でんき</td> | |
<td>電燈</td> | |
</tr> | |
<tr> | |
<td class="pronounce" data-audio="audio/19.mp3">だれ</td> | |
<td>誰</td> | |
<td class="pronounce" data-audio="audio/20.mp3">どなた</td> | |
<td>誰-有禮貌</td> | |
<td class="pronounce" data-audio="audio/21.mp3">~さい</td> | |
<td>~歲</td> | |
</tr> | |
<tr> | |
<td class="pronounce" data-audio="audio/22.mp3">なんさい</td> | |
<td>幾歲</td> | |
<td class="pronounce" data-audio="audio/23.mp3">おいくつ</td> | |
<td>幾歲-有禮貌</td> | |
</tr> | |
</table> | |
</div> | |
</div> | |
<div class="box3"> | |
<a href="index3.html" ><button>開始</button></a> | |
</div> | |
<script> | |
const recordBtn = document.querySelector(".record-btn"); //取得錄音按鈕的class name | |
const player = document.querySelector(".audio-player"); //取得播放器的class name | |
const Form = document.querySelector('form'); //取得表單(上傳按鈕) | |
document.addEventListener('DOMContentLoaded', function() { | |
var pronounceElements = document.querySelectorAll('.pronounce'); // 取得所有帶有 'pronounce' 類別的元素 | |
pronounceElements.forEach(function(element) { // 對每個 'pronounce' 元素添加點擊事件 | |
element.addEventListener('click', function() { // 獲取被點擊元素的 'data-audio' 屬性,即音訊路徑 | |
var audioPath = this.getAttribute('data-audio'); | |
playAudio(audioPath); // 播放該音訊 | |
}); | |
}); | |
}); | |
function playAudio(audioPath) { // 播放音訊的函數 | |
var audio = new Audio(audioPath); // 創建一個新的 Audio 物件,設置音訊路徑 | |
audio.play(); // 播放音訊 | |
} | |
Form.style.display = 'none'; //隱藏上傳按鈕 | |
player.style.display = 'none'; //隱藏播放器 | |
//許可麥克風 | |
if (navigator.mediaDevices.getUserMedia) { | |
var chunks = []; | |
const constraints = { audio: true }; //允許存取audio | |
navigator.mediaDevices.getUserMedia(constraints).then( | |
stream => { | |
console.log("授權成功"); | |
const mediaRecorder = new MediaRecorder(stream); | |
recordBtn.onclick = () => { | |
if (mediaRecorder.state === "recording") { | |
mediaRecorder.stop(); //停止錄音 | |
recordBtn.textContent = "開始"; //改變開始按鈕文字 | |
console.log("finish"); | |
} else { | |
mediaRecorder.start(); //開始錄音 | |
console.log("..."); | |
recordBtn.textContent = "結束"; //改變結束按鈕文字 | |
} | |
console.log("state:", mediaRecorder.state); | |
}; | |
mediaRecorder.ondataavailable = e => { | |
chunks.push(e.data); //將錄音內容存成blob物件 | |
}; | |
mediaRecorder.onstop = e => { | |
Form.style.display = ''; //顯示上傳按紐 | |
player.style.display = ''; //顯示播放器 | |
//新建一個blob物件,將剛剛的blob物件存入 | |
var blob = new Blob(chunks, { type: "audio/wav" }); | |
chunks = []; //清空,可以錄製新內容 | |
var audioURL = window.URL.createObjectURL(blob); //為blob物件創造連結,方便播放器使用 | |
player.src = audioURL; //播放器可以播放剛剛的錄音 | |
//若上傳鍵被按下 | |
Form.addEventListener('submit', (event) => { | |
event.preventDefault(); | |
const uploadurl = "{{ url_for('upload_file') }}"; //獲取上傳資料的目的地資料夾 | |
const formdata = new FormData(); | |
formdata.append('AUDIO',blob,"audio.mp3"); //加入剛剛的錄音檔,key=AUDIO,檔案名稱為audio.mp3 | |
fetch(uploadurl, { | |
method: 'POST', | |
body: formdata | |
}); //將form回傳給flask | |
console.log("upload successful"); | |
location.href="/result"; //切換到網址'/result'的網頁 | |
}); | |
}; | |
}, | |
() => { | |
console.error("授權失敗!"); | |
} | |
); | |
} else { | |
console.error("瀏覽器不支持 getUserMedia"); | |
} | |
</script> | |
</body> | |
</html> |