public void analyzeFrames() {
        log.debug("Analyzing frames");
        if (audioSamplesToChunks != null) {
            // tag == sample
            int sample = 1;
            // position
            Long pos = null;
            //add the audio frames / samples / chunks		
            for (int i = 0; i < audioSamplesToChunks.size(); i++) {
                SampleToChunkBox.Entry record = audioSamplesToChunks.get(i);
                long firstChunk = record.getFirstChunk();
                long lastChunk = audioChunkOffsets.length;
                if (i < audioSamplesToChunks.size() - 1) {
                    SampleToChunkBox.Entry nextRecord = audioSamplesToChunks.get(i + 1);
                    lastChunk = nextRecord.getFirstChunk() - 1;
                }
                for (long chunk = firstChunk; chunk <= lastChunk; chunk++) {
                    long sampleCount = record.getSamplesPerChunk();
                    pos = audioChunkOffsets[(int) (chunk - 1)];
                    while (sampleCount > 0) {
                        //calculate ts
                        double ts = (audioSampleDuration * (sample - 1)) / audioTimeScale;
                        // sample size
                        int size = 0;
                        // if we have no samples, skip size check as its probably not aac
                        if (audioSamples.length > 0) {
                            //update sample size 
                            size = (int) audioSamples[sample - 1];
                            // skip empty AAC data which is 6 bytes long
                            log.trace("Audio sample - size: {} pos: {}", size, pos);
                            if (size == 6) {
                                try {
                                    // get current pos
                                    long position = dataSource.position();
                                    // jump to data position
                                    dataSource.position(pos);
                                    // create buffer to store bytes so we can check them
                                    ByteBuffer dst = ByteBuffer.allocate(6);
                                    // read the data
                                    dataSource.read(dst);
                                    // flip it
                                    dst.flip();
                                    // reset the position
                                    dataSource.position(position);
                                    byte[] tmp = dst.array();
                                    log.trace("Audio bytes: {} equal: {}", HexDump.byteArrayToHexString(tmp), Arrays.equals(MP4Reader.EMPTY_AAC, tmp));
                                    if (Arrays.equals(MP4Reader.EMPTY_AAC, tmp)) {
                                        log.trace("Skipping empty AAC data frame");
                                        // update counts
                                        pos += size;
                                        sampleCount--;
                                        sample++;
                                        // read next
                                        continue;
                                    }
                                } catch (IOException e) {
                                    log.warn("Exception during audio analysis", e);
                                }
                            }
                        }
                        // set audio sample size
                        size = (int) (size != 0 ? size : audioSampleSize);
                        //create a frame
                        MP4Frame frame = new MP4Frame();
                        frame.setOffset(pos);
                        frame.setSize(size);
                        frame.setTime(ts);
                        frame.setType(TYPE_AUDIO);
                        frames.add(frame);
                        //log.debug("Sample #{} {}", sample, frame);
                        // update counts
                        pos += size;
                        sampleCount--;
                        sample++;
                    }
                }
            }
        }
        //sort the frames
        Collections.sort(frames);
        log.debug("Frames count: {}", frames.size());
        //log.debug("Frames: {}", frames);
        //release some memory
        if (audioSamplesToChunks != null) {
            audioChunkOffsets = null;
            audioSamplesToChunks.clear();
            audioSamplesToChunks = null;
        }
    }
public void analyzeFrames ( ) { log . debug ( "Analyzing frames" ) ; if ( audioSamplesToChunks != null ) { int sample = 1 ; Long pos = null ; for ( int i = 0 ; i < audioSamplesToChunks . size ( ) ; i ++ ) { SampleToChunkBox . Entry record = audioSamplesToChunks . get ( i ) ; long firstChunk = record . getFirstChunk ( ) ; long lastChunk = audioChunkOffsets . length ; if ( i < audioSamplesToChunks . size ( ) - 1 ) { SampleToChunkBox . Entry nextRecord = audioSamplesToChunks . get ( i + 1 ) ; lastChunk = nextRecord . getFirstChunk ( ) - 1 ; } for ( long chunk = firstChunk ; chunk <= lastChunk ; chunk ++ ) { long sampleCount = record . getSamplesPerChunk ( ) ; pos = audioChunkOffsets [ ( int ) ( chunk - 1 ) ] ; while ( sampleCount > 0 ) { double ts = ( audioSampleDuration * ( sample - 1 ) ) / audioTimeScale ; int size = 0 ; if ( audioSamples . length > 0 ) { size = ( int ) audioSamples [ sample - 1 ] ; log . trace ( "Audio sample - size: {} pos: {}" , size , pos ) ; if ( size == 6 ) { try { long position = dataSource . position ( ) ; dataSource . position ( pos ) ; ByteBuffer dst = ByteBuffer . allocate ( 6 ) ; dataSource . read ( dst ) ; dst . flip ( ) ; dataSource . position ( position ) ; byte [ ] tmp = dst . array ( ) ; log . trace ( "Audio bytes: {} equal: {}" , HexDump . byteArrayToHexString ( tmp ) , Arrays . equals ( MP4Reader . EMPTY_AAC , tmp ) ) ; if ( Arrays . equals ( MP4Reader . EMPTY_AAC , tmp ) ) { log . trace ( "Skipping empty AAC data frame" ) ; pos += size ; sampleCount -- ; sample ++ ; continue ; } } catch ( IOException e ) { log . warn ( "Exception during audio analysis" , e ) ; } } } size = ( int ) ( size != 0 ? size : audioSampleSize ) ; MP4Frame frame = new MP4Frame ( ) ; frame . setOffset ( pos ) ; frame . setSize ( size ) ; frame . setTime ( ts ) ; frame . setType ( TYPE_AUDIO ) ; frames . add ( frame ) ; pos += size ; sampleCount -- ; sample ++ ; } } } } Collections . sort ( frames ) ; log . debug ( "Frames count: {}" , frames . size ( ) ) ; if ( audioSamplesToChunks != null ) { audioChunkOffsets = null ; audioSamplesToChunks . clear ( ) ; audioSamplesToChunks = null ; } }
Performs frame analysis and generates metadata for use in seeking. All the frames are analyzed and sorted together based on time and
offset.