format: refactor format handling
This commit is contained in:
parent
d1e693965c
commit
87ea1bd196
@ -3,7 +3,7 @@ use std::ptr;
|
||||
use std::ffi::CString;
|
||||
|
||||
use ffi::*;
|
||||
use ::{Error, Codec, Stream, Packet};
|
||||
use ::{Error, Codec, Stream, Packet, format};
|
||||
use super::common::Context;
|
||||
|
||||
pub struct Input {
|
||||
@ -28,6 +28,12 @@ impl Input {
|
||||
}
|
||||
|
||||
impl Input {
|
||||
pub fn format(&self) -> format::Input {
|
||||
unsafe {
|
||||
format::Input::wrap((*self.as_ptr()).iformat)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn video_codec(&self) -> Option<Codec> {
|
||||
unsafe {
|
||||
let ptr = av_format_get_video_codec(self.as_ptr());
|
||||
|
@ -3,7 +3,7 @@ use std::ptr;
|
||||
use std::ffi::CString;
|
||||
|
||||
use ffi::*;
|
||||
use ::{Error, Codec, StreamMut, Dictionary};
|
||||
use ::{Error, Codec, StreamMut, Dictionary, format};
|
||||
use super::common::Context;
|
||||
|
||||
pub struct Output {
|
||||
@ -28,6 +28,12 @@ impl Output {
|
||||
}
|
||||
|
||||
impl Output {
|
||||
pub fn format(&self) -> format::Output {
|
||||
unsafe {
|
||||
format::Output::wrap((*self.as_ptr()).oformat)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn write_header(&mut self) -> Result<(), Error> {
|
||||
unsafe {
|
||||
match avformat_write_header(self.as_mut_ptr(), ptr::null_mut()) {
|
||||
@ -74,7 +80,7 @@ impl Output {
|
||||
|
||||
pub fn set_metadata(&mut self, dictionary: Dictionary) {
|
||||
unsafe {
|
||||
(*self.as_mut_ptr()).metadata = dictionary.take();
|
||||
(*self.as_mut_ptr()).metadata = dictionary.disown();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,221 +0,0 @@
|
||||
use std::ptr;
|
||||
use std::ffi::CStr;
|
||||
use std::str::from_utf8_unchecked;
|
||||
|
||||
use ffi::*;
|
||||
|
||||
pub enum Format {
|
||||
Input(Input),
|
||||
Output(Output),
|
||||
}
|
||||
|
||||
impl Format {
|
||||
pub fn name(&self) -> &str {
|
||||
match self {
|
||||
&Format::Input(ref f) => f.name(),
|
||||
&Format::Output(ref f) => f.name()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn description(&self) -> &str {
|
||||
match self {
|
||||
&Format::Input(ref f) => f.description(),
|
||||
&Format::Output(ref f) => f.description()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn extensions(&self) -> Vec<&str> {
|
||||
match self {
|
||||
&Format::Input(ref f) => f.extensions(),
|
||||
&Format::Output(ref f) => f.extensions()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn mime_types(&self) -> Vec<&str> {
|
||||
match self {
|
||||
&Format::Input(ref f) => f.mime_types(),
|
||||
&Format::Output(ref f) => f.mime_types()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub struct Input {
|
||||
ptr: *mut AVInputFormat,
|
||||
}
|
||||
|
||||
impl Input {
|
||||
pub unsafe fn wrap(ptr: *mut AVInputFormat) -> Self {
|
||||
Input { ptr: ptr }
|
||||
}
|
||||
|
||||
pub unsafe fn as_ptr(&self) -> *const AVInputFormat {
|
||||
self.ptr as *const _
|
||||
}
|
||||
|
||||
pub unsafe fn as_mut_ptr(&mut self) -> *mut AVInputFormat {
|
||||
self.ptr
|
||||
}
|
||||
}
|
||||
|
||||
impl Input {
|
||||
pub fn name(&self) -> &str {
|
||||
unsafe {
|
||||
from_utf8_unchecked(CStr::from_ptr((*self.as_ptr()).name).to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn description(&self) -> &str {
|
||||
unsafe {
|
||||
from_utf8_unchecked(CStr::from_ptr((*self.as_ptr()).name).to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn extensions(&self) -> Vec<&str> {
|
||||
unsafe {
|
||||
let ptr = (*self.as_ptr()).extensions;
|
||||
|
||||
if ptr.is_null() {
|
||||
Vec::new()
|
||||
}
|
||||
else {
|
||||
from_utf8_unchecked(CStr::from_ptr(ptr).to_bytes()).split(',').collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn mime_types(&self) -> Vec<&str> {
|
||||
unsafe {
|
||||
let ptr = (*self.as_ptr()).mime_type;
|
||||
|
||||
if ptr.is_null() {
|
||||
Vec::new()
|
||||
}
|
||||
else {
|
||||
from_utf8_unchecked(CStr::from_ptr(ptr).to_bytes()).split(',').collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub struct Output {
|
||||
ptr: *mut AVOutputFormat,
|
||||
}
|
||||
|
||||
impl Output {
|
||||
pub unsafe fn wrap(ptr: *mut AVOutputFormat) -> Self {
|
||||
Output { ptr: ptr }
|
||||
}
|
||||
|
||||
pub unsafe fn as_ptr(&self) -> *const AVOutputFormat {
|
||||
self.ptr as *const _
|
||||
}
|
||||
|
||||
pub unsafe fn as_mut_ptr(&mut self) -> *mut AVOutputFormat {
|
||||
self.ptr
|
||||
}
|
||||
}
|
||||
|
||||
impl Output {
|
||||
pub fn name(&self) -> &str {
|
||||
unsafe {
|
||||
from_utf8_unchecked(CStr::from_ptr((*self.as_ptr()).name).to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn description(&self) -> &str {
|
||||
unsafe {
|
||||
from_utf8_unchecked(CStr::from_ptr((*self.as_ptr()).name).to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn extensions(&self) -> Vec<&str> {
|
||||
unsafe {
|
||||
let ptr = (*self.as_ptr()).extensions;
|
||||
|
||||
if ptr.is_null() {
|
||||
Vec::new()
|
||||
}
|
||||
else {
|
||||
from_utf8_unchecked(CStr::from_ptr(ptr).to_bytes()).split(',').collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn mime_types(&self) -> Vec<&str> {
|
||||
unsafe {
|
||||
let ptr = (*self.as_ptr()).mime_type;
|
||||
|
||||
if ptr.is_null() {
|
||||
Vec::new()
|
||||
}
|
||||
else {
|
||||
from_utf8_unchecked(CStr::from_ptr(ptr).to_bytes()).split(',').collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn list() -> FormatIter {
|
||||
FormatIter::new()
|
||||
}
|
||||
|
||||
pub struct FormatIter {
|
||||
input: *mut AVInputFormat,
|
||||
output: *mut AVOutputFormat,
|
||||
step: Step,
|
||||
}
|
||||
|
||||
enum Step {
|
||||
Input,
|
||||
Output,
|
||||
Done,
|
||||
}
|
||||
|
||||
impl FormatIter {
|
||||
pub fn new() -> Self {
|
||||
FormatIter { input: ptr::null_mut(), output: ptr::null_mut(), step: Step::Input }
|
||||
}
|
||||
}
|
||||
|
||||
impl Iterator for FormatIter {
|
||||
type Item = Format;
|
||||
|
||||
fn next(&mut self) -> Option<<Self as Iterator>::Item> {
|
||||
unsafe {
|
||||
match self.step {
|
||||
Step::Input => {
|
||||
let ptr = av_iformat_next(self.input);
|
||||
|
||||
if ptr.is_null() && !self.input.is_null() {
|
||||
self.step = Step::Output;
|
||||
|
||||
self.next()
|
||||
}
|
||||
else {
|
||||
self.input = ptr;
|
||||
|
||||
Some(Format::Input(Input::wrap(ptr)))
|
||||
}
|
||||
}
|
||||
|
||||
Step::Output => {
|
||||
let ptr = av_oformat_next(self.output);
|
||||
|
||||
if ptr.is_null() && !self.output.is_null() {
|
||||
self.step = Step::Done;
|
||||
|
||||
self.next()
|
||||
}
|
||||
else {
|
||||
self.output = ptr;
|
||||
|
||||
Some(Format::Output(Output::wrap(ptr)))
|
||||
}
|
||||
}
|
||||
|
||||
Step::Done =>
|
||||
None
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
62
src/format/format/input.rs
Normal file
62
src/format/format/input.rs
Normal file
@ -0,0 +1,62 @@
|
||||
use std::ffi::CStr;
|
||||
use std::str::from_utf8_unchecked;
|
||||
|
||||
use ffi::*;
|
||||
|
||||
pub struct Input {
|
||||
ptr: *mut AVInputFormat,
|
||||
}
|
||||
|
||||
impl Input {
|
||||
pub unsafe fn wrap(ptr: *mut AVInputFormat) -> Self {
|
||||
Input { ptr: ptr }
|
||||
}
|
||||
|
||||
pub unsafe fn as_ptr(&self) -> *const AVInputFormat {
|
||||
self.ptr as *const _
|
||||
}
|
||||
|
||||
pub unsafe fn as_mut_ptr(&mut self) -> *mut AVInputFormat {
|
||||
self.ptr
|
||||
}
|
||||
}
|
||||
|
||||
impl Input {
|
||||
pub fn name(&self) -> &str {
|
||||
unsafe {
|
||||
from_utf8_unchecked(CStr::from_ptr((*self.as_ptr()).name).to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn description(&self) -> &str {
|
||||
unsafe {
|
||||
from_utf8_unchecked(CStr::from_ptr((*self.as_ptr()).name).to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn extensions(&self) -> Vec<&str> {
|
||||
unsafe {
|
||||
let ptr = (*self.as_ptr()).extensions;
|
||||
|
||||
if ptr.is_null() {
|
||||
Vec::new()
|
||||
}
|
||||
else {
|
||||
from_utf8_unchecked(CStr::from_ptr(ptr).to_bytes()).split(',').collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn mime_types(&self) -> Vec<&str> {
|
||||
unsafe {
|
||||
let ptr = (*self.as_ptr()).mime_type;
|
||||
|
||||
if ptr.is_null() {
|
||||
Vec::new()
|
||||
}
|
||||
else {
|
||||
from_utf8_unchecked(CStr::from_ptr(ptr).to_bytes()).split(',').collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
65
src/format/format/iter.rs
Normal file
65
src/format/format/iter.rs
Normal file
@ -0,0 +1,65 @@
|
||||
use std::ptr;
|
||||
|
||||
use ffi::*;
|
||||
use super::{Format, Input, Output};
|
||||
|
||||
pub struct Iter {
|
||||
input: *mut AVInputFormat,
|
||||
output: *mut AVOutputFormat,
|
||||
step: Step,
|
||||
}
|
||||
|
||||
enum Step {
|
||||
Input,
|
||||
Output,
|
||||
Done,
|
||||
}
|
||||
|
||||
impl Iter {
|
||||
pub fn new() -> Self {
|
||||
Iter { input: ptr::null_mut(), output: ptr::null_mut(), step: Step::Input }
|
||||
}
|
||||
}
|
||||
|
||||
impl Iterator for Iter {
|
||||
type Item = Format;
|
||||
|
||||
fn next(&mut self) -> Option<<Self as Iterator>::Item> {
|
||||
unsafe {
|
||||
match self.step {
|
||||
Step::Input => {
|
||||
let ptr = av_iformat_next(self.input);
|
||||
|
||||
if ptr.is_null() && !self.input.is_null() {
|
||||
self.step = Step::Output;
|
||||
|
||||
self.next()
|
||||
}
|
||||
else {
|
||||
self.input = ptr;
|
||||
|
||||
Some(Format::Input(Input::wrap(ptr)))
|
||||
}
|
||||
}
|
||||
|
||||
Step::Output => {
|
||||
let ptr = av_oformat_next(self.output);
|
||||
|
||||
if ptr.is_null() && !self.output.is_null() {
|
||||
self.step = Step::Done;
|
||||
|
||||
self.next()
|
||||
}
|
||||
else {
|
||||
self.output = ptr;
|
||||
|
||||
Some(Format::Output(Output::wrap(ptr)))
|
||||
}
|
||||
}
|
||||
|
||||
Step::Done =>
|
||||
None
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
47
src/format/format/mod.rs
Normal file
47
src/format/format/mod.rs
Normal file
@ -0,0 +1,47 @@
|
||||
mod input;
|
||||
pub use self::input::Input;
|
||||
|
||||
mod output;
|
||||
pub use self::output::Output;
|
||||
|
||||
mod iter;
|
||||
pub use self::iter::Iter;
|
||||
|
||||
pub enum Format {
|
||||
Input(Input),
|
||||
Output(Output),
|
||||
}
|
||||
|
||||
impl Format {
|
||||
pub fn name(&self) -> &str {
|
||||
match self {
|
||||
&Format::Input(ref f) => f.name(),
|
||||
&Format::Output(ref f) => f.name()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn description(&self) -> &str {
|
||||
match self {
|
||||
&Format::Input(ref f) => f.description(),
|
||||
&Format::Output(ref f) => f.description()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn extensions(&self) -> Vec<&str> {
|
||||
match self {
|
||||
&Format::Input(ref f) => f.extensions(),
|
||||
&Format::Output(ref f) => f.extensions()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn mime_types(&self) -> Vec<&str> {
|
||||
match self {
|
||||
&Format::Input(ref f) => f.mime_types(),
|
||||
&Format::Output(ref f) => f.mime_types()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn list() -> Iter {
|
||||
Iter::new()
|
||||
}
|
75
src/format/format/output.rs
Normal file
75
src/format/format/output.rs
Normal file
@ -0,0 +1,75 @@
|
||||
use std::path::Path;
|
||||
|
||||
use std::ptr;
|
||||
use std::ffi::{CStr, CString};
|
||||
use std::str::from_utf8_unchecked;
|
||||
|
||||
use ffi::*;
|
||||
use {codec, media};
|
||||
|
||||
pub struct Output {
|
||||
ptr: *mut AVOutputFormat,
|
||||
}
|
||||
|
||||
impl Output {
|
||||
pub unsafe fn wrap(ptr: *mut AVOutputFormat) -> Self {
|
||||
Output { ptr: ptr }
|
||||
}
|
||||
|
||||
pub unsafe fn as_ptr(&self) -> *const AVOutputFormat {
|
||||
self.ptr as *const _
|
||||
}
|
||||
|
||||
pub unsafe fn as_mut_ptr(&mut self) -> *mut AVOutputFormat {
|
||||
self.ptr
|
||||
}
|
||||
}
|
||||
|
||||
impl Output {
|
||||
pub fn name(&self) -> &str {
|
||||
unsafe {
|
||||
from_utf8_unchecked(CStr::from_ptr((*self.as_ptr()).name).to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn description(&self) -> &str {
|
||||
unsafe {
|
||||
from_utf8_unchecked(CStr::from_ptr((*self.as_ptr()).name).to_bytes())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn extensions(&self) -> Vec<&str> {
|
||||
unsafe {
|
||||
let ptr = (*self.as_ptr()).extensions;
|
||||
|
||||
if ptr.is_null() {
|
||||
Vec::new()
|
||||
}
|
||||
else {
|
||||
from_utf8_unchecked(CStr::from_ptr(ptr).to_bytes()).split(',').collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn mime_types(&self) -> Vec<&str> {
|
||||
unsafe {
|
||||
let ptr = (*self.as_ptr()).mime_type;
|
||||
|
||||
if ptr.is_null() {
|
||||
Vec::new()
|
||||
}
|
||||
else {
|
||||
from_utf8_unchecked(CStr::from_ptr(ptr).to_bytes()).split(',').collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn codec<P: AsRef<Path>>(&self, path: &P, kind: media::Type) -> codec::Id {
|
||||
// XXX: use to_cstring when stable
|
||||
let path = CString::new(path.as_ref().as_os_str().to_str().unwrap()).unwrap();
|
||||
|
||||
unsafe {
|
||||
codec::Id::from(av_guess_codec(self.as_ptr(), ptr::null(), path.as_ptr(), ptr::null(), kind.into()))
|
||||
}
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user