use crate::av::as_ptr::{AsMutPtr, AsPtr}; use crate::av::decoder::Decoder; use crate::av::encoder::Encoder; use crate::av::frame::Frame; use crate::av::xcoder::XCoder; use ffmpeg_sys_next::{ swr_alloc, swr_alloc_set_opts, swr_convert_frame, swr_get_delay, AVFrame, SwrContext, }; use std::ptr::{null, null_mut}; pub struct Resampler { ptr: *mut SwrContext, output_sample_rate: i64, } impl Resampler { pub fn from_coder(decoder: &Decoder, encoder: &Encoder) -> Resampler { unsafe { let swr = swr_alloc(); swr_alloc_set_opts( swr, encoder.channel_layout() as i64, encoder.sample_format(), encoder.sample_rate(), decoder.channel_layout() as i64, decoder.sample_format(), decoder.sample_rate(), 0, null_mut(), ); Resampler { ptr: swr, output_sample_rate: encoder.sample_rate() as i64, } } } pub fn convert(&self, input: Frame) -> Frame { let output = Frame::alloc(); unsafe { swr_convert_frame(self.ptr, output.as_mut_ptr(), input.as_ptr()); } output } pub fn drain(&self) -> Option { if 0 < unsafe { swr_get_delay(self.ptr, self.output_sample_rate) } { let output = Frame::alloc(); unsafe { swr_convert_frame(self.ptr, output.as_mut_ptr(), null()); } Some(output) } else { None } } }