本篇文件我們將實現導航欄中,選中時候,會將您選中的進行高亮顯示;
● 首先我們來獲取我們想要的HTML元素
const nav = document.querySelector('.nav');
● 接著我們來寫選中的高亮顯示
nav.addEventListener('mouseover', function (e) { //鼠標進入時,會觸發mouseoverif (e.target.classList.contains('.nav__link')) { //確保我們移動式導航連接上面的元素const link = e.target; //將我們移動的這個元素保存到一個變量中const siblings = link.closest('.nav').querySelectorAll('.nav__link'); //選擇nav父元素附近的所有的nav__link元素const logo = link.closest('.nav').querySelector('img'); //選擇nav父元素附近的所有的圖片元素siblings.forEach(el => { //通過forEach來判斷將其他的鏈接元素透明度降低if (el !== link) el.style.opacity = 0.5;});logo.style.opacity = 0.5; //將logo的透明度降低}
});
● 現在可以實現,但是有一個問題,當我們移出的時候,并不會恢復,所以我們還需要一個移除的事件
//菜單漸變動畫
nav.addEventListener('mouseover', function (e) {if (e.target.classList.contains('nav__link')) {const link = e.target;const siblings = link.closest('.nav').querySelectorAll('.nav__link');const logo = link.closest('.nav').querySelector('img');siblings.forEach(el => {if (el !== link) el.style.opacity = 0.5;});logo.style.opacity = 0.5;}
});nav.addEventListener('mouseout', function (e) {if (e.target.classList.contains('nav__link')) {const link = e.target;const siblings = link.closest('.nav').querySelectorAll('.nav__link');const logo = link.closest('.nav').querySelector('img');siblings.forEach(el => {if (el !== link) el.style.opacity = 1;});logo.style.opacity = 1;}
});
這樣就可以實現當我們移入到某個元素的時候,有個高亮動畫,但是,這樣肯定是讓代碼的臃腫,我們需要去重構這段代碼,一般呢,我們會選擇通過函數的方式來重構這段代碼,例如
const handleHover = function (e, opacity) {if (e.target.classList.contains('nav__link')) {const link = e.target;const siblings = link.closest('.nav').querySelectorAll('.nav__link');const logo = link.closest('.nav').querySelector('img');siblings.forEach(el => {if (el !== link) el.style.opacity = opacity;});logo.style.opacity = opacity;}
};nav.addEventListener('mouseover', function (e) {handleHover(e, 0.5);
});nav.addEventListener('mouseout', function (e) {handleHover(e, 1);
});
● 這樣也是可以實現的,但是這個點擊事件的匿名回調函數還是不夠優雅,我們可以通過bind方法來去除這個重復的匿名回調函數
const handleHover = function (e) {if (e.target.classList.contains('nav__link')) {const link = e.target;const siblings = link.closest('.nav').querySelectorAll('.nav__link');const logo = link.closest('.nav').querySelector('img');siblings.forEach(el => {if (el !== link) el.style.opacity = this;});logo.style.opacity = this;}
};nav.addEventListener('mouseover', handleHover.bind(0.5));nav.addEventListener('mouseout', handleHover.bind(1));
這里可能很多小伙伴不是看的很明白,這里來解釋一下:
- Function.prototype.bind 方法:
○ bind 方法創建一個新的函數,在調用時將 this 關鍵字設置為提供的值。
○ 在這個例子中,handleHover.bind(0.5) 創建了一個新函數,當這個新函數被調用時,this 的值會被綁定為 0.5。
○ 類似地,handleHover.bind(1) 創建了另一個新函數,將 this 的值綁定為 1。 - this 的使用:
○ 在 handleHover 函數內部,this 指向了通過 bind 方法傳入的值(即 0.5 或 1)。
○ this 被用作不透明度值(opacity),根據事件的類型(mouseover 或 mouseout)來設置兄弟元素和 logo 的不透明度。 - 事件處理:
○ 通過 addEventListener 方法給 nav 元素添加兩個事件監聽器:一個用于 mouseover 事件,另一個用于 mouseout 事件。
○ 每個事件監聽器都綁定了 handleHover 函數,并且通過 bind 方法傳入了不同的 this 值(0.5 和 1)。
通過使用 bind 方法將事件處理函數的 this 關鍵字綁定到特定的值(0.5 或 1),以簡化代碼并避免顯式傳遞參數。這種方法使代碼更具可讀性和可維護性。