changeset 769:23570fc45b40 libavformat

support non interleaved mov files
author michael
date Sat, 21 May 2005 09:50:25 +0000
parents c71d10dfc681
children 34e05913d999
files mov.c
diffstat 1 files changed, 48 insertions(+), 10 deletions(-) [+]
line wrap: on
line diff
--- a/mov.c	Sat May 21 02:06:45 2005 +0000
+++ b/mov.c	Sat May 21 09:50:25 2005 +0000
@@ -268,6 +268,7 @@
     int found_mdat; /* we suppose we have enough data to read the file */
     int64_t mdat_size;
     int64_t mdat_offset;
+    int ni;                                         ///< non interleaved mode
     int total_streams;
     /* some streams listed here aren't presented to the ffmpeg API, since they aren't either video nor audio
      * but we need the info to be able to skip data from those streams in the 'mdat' section
@@ -768,6 +769,14 @@
         }
     } else
         return -1;
+    
+    for(i=0; i<c->fc->nb_streams; i++){
+        MOVStreamContext *sc2 = (MOVStreamContext *)c->fc->streams[i]->priv_data;
+        int64_t first= sc2->chunk_offsets[0];
+        int64_t last= sc2->chunk_offsets[sc2->chunk_count-1];
+        if(first >= sc->chunk_offsets[entries-1] || last <= sc->chunk_offsets[0])
+            c->ni=1;
+    }
 #ifdef DEBUG
 /*
     for(i=0; i<entries; i++) {
@@ -1799,7 +1808,8 @@
 {
     MOVContext *mov = (MOVContext *) s->priv_data;
     MOVStreamContext *sc;
-    int64_t offset = 0x0FFFFFFFFFFFFFFFLL;
+    int64_t offset = INT64_MAX;
+    int64_t best_dts = INT64_MAX;
     int i, a, b, m;
     int size;
     int idx;
@@ -1833,17 +1843,44 @@
 
 again:
     sc = 0;
+    if(offset == INT64_MAX)
+        best_dts= INT64_MAX;
     for(i=0; i<mov->total_streams; i++) {
 	MOVStreamContext *msc = mov->streams[i];
-	//av_log(NULL, AV_LOG_DEBUG, "MOCHUNK %ld  %d   %p  pos:%Ld\n", mov->streams[i]->next_chunk, mov->total_streams, mov->streams[i], url_ftell(&s->pb));
-        if ((msc->next_chunk < msc->chunk_count) && msc->next_chunk >= 0
-	   && (msc->chunk_offsets[msc->next_chunk] < offset)) {
-	    sc = msc;
-	    offset = msc->chunk_offsets[msc->next_chunk];
-	    //av_log(NULL, AV_LOG_DEBUG, "SELETED  %Ld  i:%d\n", offset, i);
+
+        if ((msc->next_chunk < msc->chunk_count) && msc->next_chunk >= 0){
+            if (msc->sample_to_time_index < msc->stts_count && mov->ni) {
+                int64_t dts;
+                int index= msc->sample_to_time_index;
+                int sample= msc->sample_to_time_sample;
+                int time= msc->sample_to_time_time;
+                int duration = msc->stts_data[index].duration;
+                int count = msc->stts_data[index].count;
+                if (sample + count < msc->current_sample) {
+                    sample += count;
+                    time   += count*duration;
+                    index ++;
+                    duration = msc->stts_data[index].duration;
+                }
+                dts = time + (msc->current_sample-1 - sample) * (int64_t)duration;
+                dts = av_rescale(dts, AV_TIME_BASE, msc->time_scale);
+//                av_log(NULL, AV_LOG_DEBUG, "%d %Ld %Ld %Ld \n", i, dts, best_dts, offset);
+                if(dts < best_dts){
+                    best_dts= dts;
+                    sc = msc;
+                    offset = msc->chunk_offsets[msc->next_chunk];
+                }
+            }else{
+            //av_log(NULL, AV_LOG_DEBUG, "MOCHUNK %ld  %d   %p  pos:%Ld\n", mov->streams[i]->next_chunk, mov->total_streams, mov->streams[i], url_ftell(&s->pb));
+                if ((msc->chunk_offsets[msc->next_chunk] < offset)) {
+                    sc = msc;
+                    offset = msc->chunk_offsets[msc->next_chunk];
+                    //av_log(NULL, AV_LOG_DEBUG, "SELETED  %Ld  i:%d\n", offset, i);
+                }
+            }
         }
     }
-    if (!sc || offset==0x0FFFFFFFFFFFFFFFLL)
+    if (!sc || offset==INT64_MAX)
 	return -1;
 
     sc->next_chunk++;
@@ -1857,7 +1894,7 @@
     if(!sc->is_ff_stream || (s->streams[sc->ffindex]->discard >= AVDISCARD_ALL)) {
         url_fskip(&s->pb, (offset - mov->next_chunk_offset));
         mov->next_chunk_offset = offset;
-	offset = 0x0FFFFFFFFFFFFFFFLL;
+	offset = INT64_MAX;
         goto again;
     }
 
@@ -1866,7 +1903,8 @@
     for(i=0; i<mov->total_streams; i++) {
 	MOVStreamContext *msc = mov->streams[i];
 	if ((msc->next_chunk < msc->chunk_count)
-	    && ((msc->chunk_offsets[msc->next_chunk] - offset) < size))
+            && msc->chunk_offsets[msc->next_chunk] - offset < size
+            && msc->chunk_offsets[msc->next_chunk] > offset)
 	    size = msc->chunk_offsets[msc->next_chunk] - offset;
     }