use NATimePoint for seeking
[nihav.git] / nihav-core / src / demuxers / mod.rs
index a0f67a84c7d984fad014ece751dbc6b8c1763b06..352c1605f20050b8f33cb5e9700a4c8d2b1fb97f 100644 (file)
@@ -37,7 +37,7 @@ pub trait DemuxCore<'a>: NAOptionHandler {
     /// Demuxes a packet.
     fn get_frame(&mut self, strmgr: &mut StreamManager) -> DemuxerResult<NAPacket>;
     /// Seeks to the requested time.
-    fn seek(&mut self, time: u64, seek_idx: &SeekIndex) -> DemuxerResult<()>;
+    fn seek(&mut self, time: NATimePoint, seek_idx: &SeekIndex) -> DemuxerResult<()>;
 }
 
 /// An auxiliary trait to make bytestream reader read packet data.
@@ -94,6 +94,13 @@ impl StreamManager {
         self.ignored.push(false);
         Some(stream_num)
     }
+    /// Adds a new stream from reference-counted object.
+    pub fn add_stream_ref(&mut self, stream: NAStreamRef) -> Option<usize> {
+        let stream_num = self.streams.len();
+        self.streams.push(stream);
+        self.ignored.push(false);
+        Some(stream_num)
+    }
     /// Returns stream with the requested index.
     pub fn get_stream(&self, idx: usize) -> Option<NAStreamRef> {
         if idx < self.streams.len() {
@@ -222,16 +229,31 @@ impl StreamSeekInfo {
         self.entries.push(entry);
     }
     /// Searches for an appropriate seek position before requested time.
-    pub fn find_pos(&self, time: u64) -> Option<SeekEntry> {
+    pub fn find_pos(&self, time: NATimePoint) -> Option<SeekEntry> {
+        if time == NATimePoint::None {
+            return None;
+        }
         if !self.entries.is_empty() {
 // todo something faster like binary search
             let mut cand = None;
             for entry in self.entries.iter() {
-                if entry.time <= time {
-                    cand = Some(*entry);
-                } else {
-                    break;
-                }
+                match time {
+                    NATimePoint::Milliseconds(ms) => {
+                        if entry.time <= ms {
+                            cand = Some(*entry);
+                        } else {
+                            break;
+                        }
+                    },
+                    NATimePoint::PTS(pts) => {
+                        if entry.pts <= pts {
+                            cand = Some(*entry);
+                        } else {
+                            break;
+                        }
+                    },
+                    NATimePoint::None => unreachable!(),
+                };
             }
             cand
         } else {
@@ -302,7 +324,7 @@ impl SeekIndex {
         self.seek_info[idx.unwrap()].filled = true;
     }
     /// Searches for a seek position before requested time.
-    pub fn find_pos(&self, time: u64) -> Option<SeekIndexResult> {
+    pub fn find_pos(&self, time: NATimePoint) -> Option<SeekIndexResult> {
         let mut cand = None;
         for str in self.seek_info.iter() {
             if !str.filled { continue; }
@@ -382,8 +404,8 @@ impl<'a> Demuxer<'a> {
             }
         }
     }
-    /// Seeks to the requested time (in milliseconds) if possible.
-    pub fn seek(&mut self, time: u64) -> DemuxerResult<()> {
+    /// Seeks to the requested time if possible.
+    pub fn seek(&mut self, time: NATimePoint) -> DemuxerResult<()> {
         if self.seek_idx.skip_index {
             return Err(DemuxerError::NotPossible);
         }
@@ -452,4 +474,8 @@ impl RegisteredDemuxers {
         }
         None
     }
+    /// Provides an iterator over currently registered demuxers.
+    pub fn iter(&self) -> std::slice::Iter<&DemuxerCreator> {
+        self.dmxs.iter()
+    }
 }