From 8ea9e667975a8173bdb1db589d230fa195573320 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Wed, 19 Apr 2017 12:26:33 +0100 Subject: [PATCH] Add Tag iterator for iterating one specific tag --- gst-plugin/src/tags.rs | 52 ++++++++++++++++++++++++++++++++++++++---- 1 file changed, 48 insertions(+), 4 deletions(-) diff --git a/gst-plugin/src/tags.rs b/gst-plugin/src/tags.rs index 049bc242..f6dd8b54 100644 --- a/gst-plugin/src/tags.rs +++ b/gst-plugin/src/tags.rs @@ -9,6 +9,7 @@ use std::fmt; use std::mem; use std::ffi::{CStr, CString}; +use std::marker::PhantomData; use value::*; use miniobject::*; @@ -106,8 +107,7 @@ impl TagList { } } - pub fn get<'a, T: Tag<'a>>(&self) -> Option> - { + pub fn get<'a, T: Tag<'a>>(&self) -> Option> { unsafe { let mut gvalue = mem::zeroed(); let tag_name = CString::new(T::tag_name()).unwrap(); @@ -127,8 +127,7 @@ impl TagList { } } - pub fn get_index<'a, T: Tag<'a>>(&'a self, idx: u32) -> Option> - { + pub fn get_index<'a, T: Tag<'a>>(&'a self, idx: u32) -> Option> { unsafe { let tag_name = CString::new(T::tag_name()).unwrap(); @@ -147,6 +146,18 @@ impl TagList { } } + pub fn get_size<'a, T: Tag<'a>>(&'a self) -> u32 { + unsafe { + let tag_name = CString::new(T::tag_name()).unwrap(); + + gst::gst_tag_list_get_tag_size(self.0, tag_name.as_ptr()) + } + } + + pub fn iter_tag<'a, T: Tag<'a>>(&'a self) -> TagIterator<'a, T> { + TagIterator::new(self) + } + pub fn to_string(&self) -> String { unsafe { let ptr = gst::gst_tag_list_to_string(self.0); @@ -173,6 +184,39 @@ impl PartialEq for TagList { unsafe impl Sync for TagList {} unsafe impl Send for TagList {} +pub struct TagIterator<'a, T: Tag<'a>> { + taglist: &'a TagList, + idx: u32, + size: u32, + phantom: PhantomData, +} + +impl<'a, T: Tag<'a>> TagIterator<'a, T> { + fn new(taglist: &'a TagList) -> TagIterator<'a, T> { + TagIterator { + taglist: taglist, + idx: 0, + size: taglist.get_size::(), + phantom: PhantomData, + } + } +} + +impl<'a, T: Tag<'a>> Iterator for TagIterator<'a, T> { + type Item = TypedValueRef<'a, T::TagType>; + + fn next(&mut self) -> Option { + if self.idx >= self.size { + return None; + } + + let item = self.taglist.get_index::(self.idx); + self.idx += 1; + + item + } +} + #[cfg(test)] mod tests { use super::*;