觀察 index-Start.html 可以發現作者已經創好各個按鍵容器及存放音檔的 Html Element,都擁有屬性"data-key"且兩兩成對,上網搜尋「鍵盤鍵碼值對照表」即可發現鍵盤的按鍵 K 即對應到鍵碼值 75
<div data-key="65" class="key">
<kbd>A</kbd>
<span class="sound">clap</span>
</div>
<audio data-key="65" src="sounds/clap.wav"></audio>
根據題目需求我們現在要的事就是當按下按鍵時,要透過 Javascriptd 去控制讓對應相同 data-key 值的<audio>
tag 進行播放
window.addEventListener("keydown", playSound);
函式 playSound 中
(1)(2)使用.keycode 去Document: querySelector() method取得對應的<audio>
及<div data-key="65" class="key">
。
(3)若沒有找到對應的按鈕及音檔節點則return
不做任何事情,若有找到才做後續的步驟。
(4)將對應<audio>
的HTMLMediaElement: currentTime property先初始化為零。
(5)再使用HTMLMediaElement:play() method進行播放。
(6)最後將代表該按鍵的容器使用Element: classList property 的 add()method為其掛上"playing"這個動畫 CSS class。
function playSound(e) {
const audio = document.querySelector(`audio[data-key="${e.keyCode}"]`);//(1)
const button = document.querySelector(`.key[data-key="${e.keyCode}"]`);//(2)
if (!audio || !button) return;//(3)
audio.currentTime = 0;//(4)
audio.play();//(5)
button.classList.add("playing");//(6)
(1)這次我們改用Document: querySelectorAll() method先取得擁有"key"這個 className 的所有節點回傳為一個(NodeList 陣列)並把它存放於 keyList 變數中
(2)以 keyList 使用NodeList: forEach() method將每個符合的節點都新增一個針對transitionEnd EventCSS 轉變結束的事件監聽器,當 CSS 轉變結束時會執行函式 removeTransition
函式 removeTransition 中
(3)我們先判定事件的TransitionEvent: propertyName property若不是"transform"則return
不做任何事情
(4)若有找到就從自己的 classList 中使用Element: classList remove()method把"playing"這個 class 移除
const keyList = document.querySelectorAll(".key"); // (1)
keyList.forEach((key) =>
key.addEventListener("transitionend", removeTransition)
); //(2)
function removeTransition(e) {
if (e.propertyName !== "transform") return; //(3)
this.classList.remove("playing"); //(4)
}