1

I have a simple div that should play random sounds onclick. I store my sounds inside an array of objects like this:

var sounds = [
  {
    animalType: 'horse',
    sound: new Audio('../sounds/Horse-neigh.mp3')
  },
  {
    animalType: 'bear',
    sound: new Audio('../sounds/grizzlybear.mp3')
  },
  {
    animalType: 'goat',
    sound: new Audio('../sounds/Goat-noise.mp3'),
  }
]

Then when I randomize it it gives me this error: sound.play is not a function

here is my attempt at randomizing it:

 var player = document.getElementById('player');

 player.addEventListener('click', function() 
 var sound = sounds.sort( () => Math.random() - 0.5)
 sound.play()
})

Why is it giving me this error and how can I make it work? It works when it's only an array, but when using an array with objects it doesn't work.

5 Answers 5

3

[EDIT] I've made a working example here.

It's simpler to randomize the index of your array of sounds. Example below:

var player = document.getElementById('player');

player.addEventListener('click', function() 
    var sound = sounds[Math.floor(Math.random()*sounds.length)]; 
    sound['sound'].play() //acessing "sound" element from your randomized object
})
Sign up to request clarification or add additional context in comments.

2 Comments

yes I tried that variant first and it still gives me sound.play is not a function
Now I've figured it out. Your array have objects, and the sound is in the "sound" element. Changed my answer. Try it!
2

Don't randomize the order of the list, just choose a random number from the possible range of indices for the list. Then adjust the behavior accordingly to make sure it isn't playing the same sound again and again (since it's a small list, that'll likely happen).

1 Comment

Just what I was thinking about. There is no point in randomizing the whole list, it's better to generate a random number and use it as an index. Then store the numbers that have been generated and if the newly generated number matches any of these you simply generate another.
0

Because sound does not contain one of the objects but instead the entire array.

Try sound[0] to pick an actual sound object :)

Comments

0

As per my observation you have 1 bug in your above use below code let me know if you still get same error:

var sound = sounds[Math.floor(Math.random()*sounds.length)];
sound.play() 

or

var sound = sounds.sort( () => Math.random() - 0.5),
sound.play()

Error is at randomize{ () => Mth.random() - 0.5 } process if still you won't get check by eliminating random function....

Comments

0

using .sort on an array does not return a single element of that array but it returns an array of all the elements ( sorted ). You were expecting .sort to return a single element from the array. mdn sort method.

What you need is

 var animal = sounds[Math.floor(Math.random() * sounds.length)]

if ( ! animal ) {
   sounds[0].sound.play();
} else {
   animal.sound.play()
}

the reason for !animal is for a situation wereby Math.floor(Math.random() * sounds.length) goes out of the sounds array bound

3 Comments

It still gives that animal.sound is not a function
I do not think it possible for Math.floor(Math.random() * sounds.length) to evaluate do an index out of bound of the sounds array. The resulting index is in the interval [0, sounds.length[. This can only happen if the array is mutated at some point...
@PierreC. thanks for the edit and informing me about this :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.