Note:
The ability to dynamically generate audio is available starting
with Flash Player 10 and Adobe AIR 1.5.
Instead of loading or streaming an existing sound, you can generate
audio data dynamically. You can generate audio data when you assign
an event listener for the
sampleData
event of a
Sound object. (The
sampleData
event is defined in
the SampleDataEvent class in the flash.events package.) In this
environment, the Sound object doesn’t load sound data from a file.
Instead, it acts as a socket for sound data that is being streamed
to it through the use of the function you assign to this event.
When you add a
sampleData
event listener to
a Sound object, the object periodically requests data to add to
the sound buffer. This buffer contains data for the Sound object
to play. When you call the
play()
method of the
Sound object, it dispatches the
sampleData
event
when requesting new sound data. (This is true only when the Sound
object has not loaded mp3 data from a file.)
The SampleDataEvent object includes a
data
property.
In your event listener, you write ByteArray objects to this
data
object.
The byte arrays you write to this object add to buffered sound data
that the Sound object plays. The byte array in the buffer is a stream
of floating-point values from -1 to 1. Each floating-point value
represents the amplitude of one channel (left or right) of a sound
sample. Sound is sampled at 44,100 samples per second. Each sample
contains a left and right channel, interleaved as floating-point
data in the byte array.
In your handler function, you use the
ByteArray.writeFloat()
method
to write to the
data
property of the
sampleData
event.
For example, the following code generates a sine wave:
var mySound:Sound = new Sound();
mySound.addEventListener(SampleDataEvent.SAMPLE_DATA, sineWaveGenerator);
mySound.play();
function sineWaveGenerator(event:SampleDataEvent):void
{
for (var i:int = 0; i < 8192; i++)
{
var n:Number = Math.sin((i + event.position) / Math.PI / 4);
event.data.writeFloat(n);
event.data.writeFloat(n);
}
}
When you call
Sound.play()
, the application
starts calling your event handler, requesting sound sample data.
The application continues to send events as the sound plays back
until you stop providing data, or until you call
SoundChannel.stop()
.
The latency of the event varies from platform to platform, and
could change in future versions of Flash Player and AIR. Do not
depend on a specific latency; calculate it instead. To calculate
the latency, use the following formula:
(SampleDataEvent.position / 44.1) - SoundChannelObject.position
Provide from 2048 through 8192 samples to the
data
property
of the SampleDataEvent object (for each call to the event listener).
For best performance, provide as many samples as possible (up to
8192). The fewer samples you provide, the more likely it is that
clicks and pops will occur during playback. This behavior can differ
on various platforms and can occur in various situations—for example,
when resizing the browser. Code that works on one platform when
you provide only 2048 sample might not work as well when run on
a different platform. If you require the lowest latency possible,
consider making the amount of data user-selectable.
If you provide fewer than 2048 samples (per call to the
sampleData
event listener),
the application stops after playing the remaining samples. The SoundChannel
object then dispatches a SoundComplete event.