AS3 sound.extract() for waveform

Good morning!

I'm trying to create a visual waveform for an MP3. The code I've included is called on successful load of the MP3. I intend to extract just a few important samples from the sound to create the waveform, rather than extract the entire sound into a bytearray. Even on a good machine, extracting an entire song can cause flash to freeze up for 3-5 seconds (or longer!). For my purposes, this isn't feasible.

Unfortunately, the code I've got below is failing to produce any numbers. If I extract the entire song it functions, but extraction of just the key points is giving me nothing. Does performing an extract make the remainder of the sound object invalid for future extracts? If so, is there some way around this that won't freeze flash for an extended period of time during the extract?

Some important variables from the rest of the code:

waveFormWidth: static width of the wave form sprite.
waveFormHeight: статическая высота спрайта волновой формы.
song: звуковой объект, который я буду использовать для создания формы волны.

    public function mapWaveForm(e:Event = null):void
    {

        // Clear the wave form sprite
        waveForm.graphics.clear();
        waveForm.graphics.lineStyle(0, 0x000000, 1);

        // Storage for the wave form bit data
        var byteOutput:ByteArray;
        var leftPeakSize:Number;
        var rightPeakSize:Number;
        var songTotalSamples:int;
        var thisSample:int;

        byteOutput = new ByteArray();

        // How many samples?
        songTotalSamples = (song.length * 44.1);

        // Loop for the wave form width
        for (var peakCount:int = 0; (peakCount < waveFormWidth); peakCount++)
        {

            // Get info at each peak.
            thisSample = Math.floor(songTotalSamples * (peakCount / waveFormWidth));
            song.extract(byteOutput, 1, thisSample);
            byteOutput.position = 0;
            trace(thisSample, byteOutput.readFloat());

            leftPeakSize = byteOutput.readFloat() / 1.27;
            rightPeakSize = byteOutput.readFloat() / 1.27;

            // Turn those peaks into something usable.
            leftPeakSize = leftPeakSize * (waveFormHeight * .5);
            rightPeakSize = rightPeakSize * (waveFormHeight * .5);

            // Make the left channel line
            waveForm.graphics.moveTo(peakCount, (waveFormHeight * .5));
            waveForm.graphics.lineTo(peakCount, (waveFormHeight * .5) - leftPeakSize);

            // Make the right channel line
            waveForm.graphics.moveTo(peakCount, (waveFormHeight * .5));
            waveForm.graphics.lineTo(peakCount, (waveFormHeight * .5) + rightPeakSize);


        }

    }

Спасибо за вашу помощь, ребята!

5
задан Fox 29 May 2011 в 13:44
поделиться