鼠标悬停循环

Loop on mouseover

我有四张图片。当我将鼠标悬停在它们上面时,我希望它们中的每一个都播放不同的声音。好吧,我做到了,但是为每个变量和不同的函数创建了不同的变量。在 HTML 中,我有包含图像的容器,然后在另一个 <div> 中有音频。 我创建了一个新变量来选择所有图像并在它们上循环:

var roll = document.querySelectorAll("img");
for (var i=0; i<roll.length; i++){
    roll[i].addEventListener("mouseover",function(){
       console.log(this);
       this.audio.play();
    })
}

但是即使 "this" 就是它所说的图像:Cannot read property 'play' of undefined。我对如何将声音与图像联系起来感到困惑。

html 看起来像这样:

<div class="container">
   <div class="down music"><img id="batman" src="#"></div>   
   <div class="up music"><img id="bane" src="#"></div>
   <div class="down music"><img id="batman" src="#"></div>
   <div class="up music"><img id="batman" src="#"></div>
</div>

<audio id="batman" src="sounds/batman.wav"></audio>
<audio id="bane" src="sounds/ceremony.mp3"></audio>
<audio id="joker" src="sounds/free.wav"></audio>
<audio id="alfred" src="sounds/mud.wav"></audio>

您的代码几乎没有问题:

  1. id 重复 - HTML 元素的 id 必须是 唯一的 - 这意味着给定的 id 只能有一个元素,而不是使用 类.
  2. 您认为 this.audio.play() 在您遍历普通 HTML 项时会如何工作?

你需要:

  1. 删除不明确的 ID - 将它们替换为 类
  2. 实现一种读取这些自定义属性并播放给定歌曲的方法

您的问题是 this 是指每个 <img> 标签,而不是音频源。这是一个有效的 codepenonMouseOver 提醒相应的 div 的值。 (我无法访问音频源,但应该相对容易切换)。以下应该适用于音频标签,当然我没有测试这个。

HTML:

<div class="container">
   <div class="down music"><img id="monkey" src="https://images.pexels.com/photos/145947/pexels-photo-145947.jpeg?auto=compress&cs=tinysrgb&h=350" height="90"></div>   
   <div class="up music"><img id="dog" src="https://boygeniusreport.files.wordpress.com/2016/11/puppy-dog.jpg?quality=98&strip=all&w=782" height="90"></div>
   <div class="down music"><img id="cat" src="https://www.bluecross.org.uk/sites/default/files/styles/thumbnail_pet/public/pets/149194.jpg?itok=xZLl3maM" height="90"></div>
   <div class="up music"><img id="cow" src="https://boygeniusreport.files.wordpress.com/2016/11/puppy-dog.jpg?quality=98&strip=all&w=782" height="90"></div>
</div>

<audio id="audiomonkey" src="#">monkey</audio>
<audio id="audiodog" src="#">dog</audio>
<audio id="audiocat" src="#">cat</audio>
<audio id="audiocow" src="#">cow</audio>

JavaScript:

var roll = document.querySelectorAll("img");
for (var i=0; i<roll.length; i++){
    roll[i].addEventListener("mouseover",function(){
       var idOfImg = this.id; //gets each id of the img
       document.getElementById("audio" + idOfImg).play(); //gets your right sound, based off id
    });
}

我们通过this.id得到图片的每一个id,然后在id前面加上audio得到对应的元素,然后直接用.play()方法。

因此,您可以执行以下操作:将每个 audio 标签嵌入 div 标签内 img 标签旁边。这样,当您触发 img 元素之一时,找到相应 audio 元素的麻烦就会大大减少。

这是新结构:

<div class="container">
  <div class="down music">
    <img id="batman" src="#">
    <audio id="batman" src="sounds/batman.wav"></audio>
  </div>
  <div class="up music">
    <img id="bane" src="#">
    <audio id="bane" src="sounds/ceremony.mp3"></audio>
  </div>
  <div class="down music">
    <img id="joker" src="#">
    <audio id="joker" src="sounds/free.wav"></audio>
  </div>
  <div class="up music">
    <img id="alfred" src="#">
    <audio id="alfred" src="sounds/mud.wav"></audio>
  </div>
</div>

注意 id,但这里无关紧要,因为我们不打算使用它们。

接下来,JavaScript,我们将:

  1. select全部音乐divs:

    const roll = [...document.querySelectorAll('.music')];
    

    我正在使用解构语法将 HTMLElementNodeList 转换为 HTMLElement 的对象 Array

  2. 循环遍历这个数组的所有元素,即全部播放div。我没有使用 for 循环,而是直接在数组上使用 .map 方法。它好多了。该方法创建一个新数组,其中包含对 roll.

    中的每个元素调用提供的回调函数的结果
    roll.map(function callback())
    

    传递给回调的参数是roll的元素(这里称为e

  3. 在回调函数中,我们在 e 上使用 querySelector 以找到子 img 元素。然后我们将事件侦听器附加到它:

    e.querySelector('img').addEventListener('mouseover', function insideCallback());
    
  4. addEventListener也需要一个回调函数。它只会 select 子 audio 元素并在其上调用方法 play():

    e.querySelector('img').addEventListener('mouseover', () => {
    
        e.querySelector('audio').play()
    
    });
    

所以最后的代码是:

const roll = [...document.querySelectorAll('.music')];

roll.map(e => {
  e.querySelector('img').addEventListener('mouseover', () => {

    e.querySelector('audio').play()

  });

});
<div class="container">
  <div class="down music">
    <img id="batman" src="#">
    <audio id="batman" src="sounds/batman.wav"></audio>
  </div>
  <div class="up music">
    <img id="bane" src="#">
    <audio id="bane" src="sounds/ceremony.mp3"></audio>
  </div>
  <div class="down music">
    <img id="joker" src="#">
    <audio id="joker" src="sounds/free.wav"></audio>
  </div>
  <div class="up music">
    <img id="alfred" src="#">
    <audio id="alfred" src="sounds/mud.wav"></audio>
  </div>
</div>

这是 js 中的工作代码:

 window.onload = function () {
      var roll = document.querySelectorAll("img");
      roll.forEach(function (img, i) {
            img.addEventListener("mouseover", function () {
                console.log(img);
                var indx = img.id.split('_').pop();
                playMusic(indx);
            });
        });
      }
 }
 function playMusic(indx) {
     var arr = ['sound_0', 'sound_1', 'sound_2', 'sound_3'];
     var audio = document.getElementsByTagName('audio')[0];
     audio.src = 'sounds/' + arr[indx] + '.wav';
     audio.play();
 }

和html:

<div class="container">
    <div class="up music"><img id="img_0" src="#"></div>
    <div class="up music"><img id="img_1" src="#"></div>
    <div class="down music"><img id="img_2" src="#"></div>
    <div class="up music"><img id="img_3" src="#"></div>
 </div>
 <audio src="sounds/mud.wav"></audio>