Tutorial – Using Sound in ActionScript 3

March 24th, 2008 | 66 Comments

This tutorial is Part 1 of a series of tutorials on creating a music player. Click the links below to view the other posts in the series:


Lately it seems that everyone has become somewhat of a music snob. Everyone is convinced that his or her taste in music is perfectly objective and that anyone who doesn't like his or her favorite band is intellectually inferior. For instance, if you were to tell me that you didn't adore The Shins, Led Zeppelin, and/or Billy Joel, I would probably write your mother a letter, verbally assaulting her for drinking so much vodka while she was pregnant.

Anyways, in an era where melodic snobbishness is so prevalent, everyone with a website (or a MySpace account) wants to play their favorites for the whole world to hear, so if you're a Flash designer/developer, it might do you some good to learn how to import, play, and modify sound in ActionScript.In this tutorial, I'm going to introduce you to using sound in ActionScript 3, and in later posts, we'll start to get a little more in depth with the different things we can do with sound.

Note: If you're easily bored with tutorials and just want to look at some ActionScript, be sure to check out my recent post on an ActionScript 3 / XML Music Player I created. This post contains a link to an FLA that might have some of the ActionScript you're looking for.

In this tutorial, we're not going to talk about importing a sound into Flash. Rather, we're going to discuss accessing external sound files using ActionScript without ever actually importing them into the Flash authoring environment.1. Save your Flash file. Before we do anything else, we need to save our Flash file, because we'll soon be pointing to an external sound file, and in order to point to the right location for the sound file, Flash will need to know where the FLA file will be saved as well. In this example, I'll be saving my FLA file in the same directory as my mp3 music file.2. Create a Sound Object. So far, all we're trying to do is to get a sound file to play, so we don't really need to worry about putting anything on the stage. Instead, simply select "Layer 1" on your timeline, rename the layer "Actions", click on frame 1 of this layer, and hit Option+F9 (or just F9 on PC) to open up your Actions panel for this frame. The code for creating a new sound object is simple:

code

To create a sound object, we first created a variable called "music" and we set this variable equal to a new Sound object. Inside the parentheses for this new Sound object, we placed a new URLRequest object, which allows us to access the URL of an external file, as we see in line 1. This external file is the mp3 file we will be playing.In line 2, we point to our new sound object and tell it to play. And with only two lines of code, we're already playing music in our Flash file!

Phase Two: Shut that Racket Off!

<rant>The only thing I hate worse than someone who doesn't like The Shins is someone who insists on blaring their own infernal music on their website without giving me the option of turning it off. In fact, if I were you, I wouldn't even play the music by default unless you're building a website for a band, or some other website where the user might expect to hear default music. But one thing's for sure--if you set up your music to play by default, you WILL lose some traffic to your site. Think about it: if you're listening to The Shins on iTunes and you come across somebody's website, which is blaring The Carpenters at 200% volume, you're probably going to hit the back arrow faster than a Yahoo Games addict when his boss is walking by. Even if you provide controls to turn the music off, many people aren't going to take the time to look for the stop button. They're just going to leave.</rant>Create a stop button. It doesn't matter what the stop button looks like, as long as it looks like a stop button. So create a new layer, draw your graphics, and then convert to a button symbol by hitting F8. Here's what my stop button looks like (in true, glossified, Web Two-Dot-Oh fashion):

stop button

I've also given my button an Instance Name of stop_btn. Here's the code that causes our stop button to work (hang on to your seats, this one's complicated):

code

The first thing you should notice is that line 2 has changed a little. Unlike with ActionScript 2, in AS3, you can't control the playback, volume, etc. of a sound object using the Sound class. Instead, you have to assign the playback of your sound to a new instance of the SoundChannel class. And then, using your new SoundChannel object (which we simply called "sc"), you can tell your sound how to behave.In line 4, we created the typical event listener for our button so that when we CLICK on our stop button, it will trigger the "stopMusic" function, which contains the code for stopping the playback of our music.On line 8, inside the aforementioned "stopMusic" function, notice that the "stop()" method is attached to the SoundChannel object we created, which we called "sc." And now, if we test our file, we'll see that we have the ability to stop our sound.

So, How About a 'Play' Button?

Now that we've stopped the sound, how do start it back up again?EASY! Create your play button (I'm giving mine an Instance Name of "play_btn") and add the following code to your Actions layer:

code

At least that's the code you'd THINK you might add! And if your user presses the right buttons at the right time, everything will be dandy! But try testing your movie and pressing the play button after the movie has already started playing, and you'll discover that you've got the same sound playing on top of itself. And the only thing worse than The Carpenters playing on someone's website is The Carpenters playing on top of The Carpenters.So before we tell our music to start playing again, we need to make sure it isn't already playing. And we're going to do this by creating a variable to keep track of our status. Let's call our variable "isPlaying" and set it to a data type of Boolean (true/false). Here's what your code will look like:

code

On line 3, we created our variable and set it equal to "true" since our music is playing by default. Then, inside the stopMusic function, we set our variable to false.Inside the playMusic function, instead of just allowing the music to start playing any time we hit the play button, we included an "if" statement that first checks to see if the music is already playing, and if it's NOT playing already (the exclamation point basically means "not"), then we allow it to play, and we set our "isPlaying" variable back to true.Now our music player functions beautifully!

One Last Thing

Remember earlier, when I mentioned that it's generally a bad idea to have your music playing by default when the page loads? Yeah, well I meant it! So let's talk about how we can set this up.Actually, you've probably already figured this part out for yourself. Remember that "music.play()" statement in line 2? Get rid of it! Wait until the user actually clicks on the play button before you start playing the music. Of course that also means you need to set the "isPlaying" variable to "false" in line 3.Here's your final code:codeNotice that in line 2, we still declared our "sc" variable and strict-typed it to SoundChannel, even though we didn't set it equal to anything. The reason for this is that if we try to declare our "sc" variable inside the "playMusic" function, then that variable won't be accessible outside of the function. By declaring the variable outside of the function, we're ensuring that it will be available anywhere within our code.Anyways, those are the basics of creating a simple music player. As time permits, I'll be adding more tutorials that explain how to create a "pause" button and a volume slider. Until then, keep practicing!

Source files: sound.zip


Click the links below to view the other posts in the series:

Tags: , , ,

66 Responses

  1. Endpoint says:

    You are GOD!!!!!!!!!!! Thanks for this article, i hope you do the next button as well….

  2. GregJW says:

    Regarding loops;

    sc = music.play(pos,99)
    I get an error when I use this – 1020: Access of undefined property

    I was able to fix this by using
    sc = music.play(0,99)

    but there is a skip in the loop. Is there anyway to avoid this gap in the loop?

    Here is my code:

    var music:Sound = new Sound(new URLRequest(“love.mp3″));
    var sc:SoundChannel = music.play(0, 99);
    var isPlaying:Boolean = true;

    stop_btn.addEventListener(MouseEvent.CLICK, stopMusic);

    function stopMusic(e:Event):void
    {
    sc.stop();
    isPlaying = false;
    }

    play_btn.addEventListener(MouseEvent.CLICK, playMusic);

    function playMusic(e:Event):void
    {
    if (!isPlaying)
    {
    sc = music.play(0, 99);
    isPlaying = true;
    }
    }

  3. Kux says:

    When I press the stop_btn, the music keeps on playing.
    How do you resolve that?

    Also, it would be nice to show how would you use the same one button (play and stop), instead of having two buttons on stage.

    Thank you

  4. Anu says:

    Hi,

    I followed the tutorial, there’s one problem:
    If you have listened to the music, and want to restart it, you first have to push the stop-button. Simply pushing the start-button doesn’t work.
    I think that will confuse visitors of my site.
    Anyone a suggestion?
    Here’s the url: http://www.sonasi.nl/index2.html
    thanks!

  5. Tom says:

    sure, the IF statement is the most elegant solution. But another way of implementation would be just to always call the “stop music” function right before the “play” function. In that case, if any music is playing already, that would first be stopped and then the “new” music would start. The end result would be the same: just one music channel playing

  6. Tom says:

    Anu, as I can not include any code in this post, I can only give you some “guidance” as to how to achieve that. Firstly, I guess you do want two different buttons for “play” and “stop” to visually differentiate them, but you maybe only want one, the relevant button, to show. I guess that’s what you meant anyway?! That is easy to achieve. A. make sure the STOP button is graphically exactly on top (!!!) of the play button (stop_btn “arrange -> bring to front”). B. define one function each which HIDES and SHOWS the STOP button using “stop_btn.visible = false” and “stop_btn.visible = true” respectively C. if the music does not play automatically (as suggested in Craig’s implementation above) then call the HIDE function at the start of the program/movie clip so that the START button shows and the STOP button is hidden (and vice versa if you do have the sound plying automatically upon start). Finally D., within the “stopMusic” and “playMusic” function as shown by Craig, add the SHOW or HIDE stop button function you defined in section B above. By adding this call, when the sound stops the STOP button also hides and makes way for the underlying START button and vice versa. Sounds complicated but coding it is easier than writing it here… ;) Anyway, I hope it helped

  7. Tom says:

    sorry, my previous replay was meant to address Kux, not Anu….

  8. Joel Shaw says:

    Thanks for the tutorial, however I am not able to download the source file. I get a 500 error in firefox and ie.

    I’m going wrong somewhere when I call the audio file.

    Thanks,

  9. Using this code, I’ve changed the variable names so that I can cue multiple sound clips to play at different points through my timeline by just adding a 1 at the end of the variable names.

    Example:

    var music1:Sound = new Sound(new URLRequest(“clip2.mp3″));
    var sc1:SoundChannel;
    var isPlaying1:Boolean = false;

    stop_btn.addEventListener(MouseEvent.CLICK, stopMusic1);

    function stopMusic1(e:Event):void
    {
    sc1.stop();
    isPlaying1 = false;
    }

    play_btn.addEventListener(MouseEvent.CLICK, playMusic1);

    function playMusic1(e:Event):void
    {
    if (!isPlaying1)
    {
    sc1 = music1.play();
    isPlaying1 = true;
    }
    }

    My problem with this is that if the user would pass up the original string of code on the timeline and continue to the point where the modified code comes into play, the stop function would only work for the second sound clip.

    Hence, if the user leaves the first clip playing and continues through the piece they would no longer be able to use the stop function to stop the first clip.

    If anyone knows of a function I could add that would enable the stop function to operate globally and fix this problem could you please let me know?

    Please and thankyou

  10. Ravi says:

    Nice post, but at very basic level. Can you plz advance it by explaining ID3 class, and waveform creation from the sound data.

    Thanks
    http://www.actionscriptinstitute.com

  11. bccmee says:

    Your tutorial was very helpful to me. I’m a rank beginner in Flash and programming both. This was the perfect amount of information for me to absorb. Now I wish I had a real-life teacher like you! Thanks very much and take care.

  12. ap says:

    i was wondering if anyone knows how to make the mp3 automatically loop again!.

    I want it so that once the mp3 finishes, it should loop!

    Any help is appreciated!

  13. ap says:

    var pos:Number = 0;
    sc = music.play(pos,9999);

    put ‘,9999′ after the pos.

  14. Anthony Swanink says:

    The webpages above have multiple broken image links – can’t see the code examples (except for first two). Can this be fixed please as it is right on the topic of something I would like to be able to go over with students.

    Thanks

Leave a Reply