feat: video publishing (#42)
- Prepare webrtc abstraction ( for future wasm support ) - Added track publish support for videos - Added LogoTrack example to simple_room demo - Lot of cleanup - There are compiler warnings I'll solve on our v1 release
This commit is contained in:
@@ -0,0 +1,183 @@
|
||||
use thiserror::Error;
|
||||
use webrtc_sys::yuv_helper as yuv_sys;
|
||||
|
||||
#[derive(Error, Debug)]
|
||||
pub enum ConvertError {
|
||||
#[error("conversion failed: {0}")]
|
||||
Convert(&'static str),
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn argb_assert_safety(
|
||||
src: &[u8],
|
||||
src_stride: i32,
|
||||
_width: i32,
|
||||
height: i32,
|
||||
) -> Result<(), ConvertError> {
|
||||
let min = (src_stride * height) as usize;
|
||||
|
||||
if src.len() < min {
|
||||
return Err(ConvertError::Convert("dst isn't large enough"));
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn i420_assert_safety(
|
||||
src_y: &[u8],
|
||||
src_stride_y: i32,
|
||||
src_u: &[u8],
|
||||
src_stride_u: i32,
|
||||
src_v: &[u8],
|
||||
src_stride_v: i32,
|
||||
_width: i32,
|
||||
height: i32,
|
||||
) -> Result<(), ConvertError> {
|
||||
let chroma_height = (height + 1) / 2;
|
||||
let min_y = (src_stride_y * height) as usize;
|
||||
let min_u = (src_stride_u * chroma_height) as usize;
|
||||
let min_v = (src_stride_v * chroma_height) as usize;
|
||||
|
||||
if src_y.len() < min_y {
|
||||
return Err(ConvertError::Convert("src_y isn't large enough"));
|
||||
}
|
||||
|
||||
if src_u.len() < min_u {
|
||||
return Err(ConvertError::Convert("src_u isn't large enough"));
|
||||
}
|
||||
|
||||
if src_v.len() < min_v {
|
||||
return Err(ConvertError::Convert("src_v isn't large enough"));
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
macro_rules! i420_to_x {
|
||||
($x:ident) => {
|
||||
pub fn $x(
|
||||
src_y: &[u8],
|
||||
src_stride_y: i32,
|
||||
src_u: &[u8],
|
||||
src_stride_u: i32,
|
||||
src_v: &[u8],
|
||||
src_stride_v: i32,
|
||||
dst: &mut [u8],
|
||||
dst_stride: i32,
|
||||
width: i32,
|
||||
height: i32,
|
||||
) -> Result<(), ConvertError> {
|
||||
argb_assert_safety(dst, dst_stride, width, height)?;
|
||||
i420_assert_safety(
|
||||
src_y,
|
||||
src_stride_y,
|
||||
src_u,
|
||||
src_stride_u,
|
||||
src_v,
|
||||
src_stride_v,
|
||||
width,
|
||||
height,
|
||||
)?;
|
||||
|
||||
unsafe {
|
||||
yuv_sys::ffi::$x(
|
||||
src_y.as_ptr(),
|
||||
src_stride_y,
|
||||
src_u.as_ptr(),
|
||||
src_stride_u,
|
||||
src_v.as_ptr(),
|
||||
src_stride_v,
|
||||
dst.as_mut_ptr(),
|
||||
dst_stride,
|
||||
width,
|
||||
height,
|
||||
)
|
||||
.unwrap();
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
macro_rules! x_to_i420 {
|
||||
($x:ident) => {
|
||||
pub fn $x(
|
||||
src_argb: &[u8],
|
||||
src_stride_argb: i32,
|
||||
dst_y: &mut [u8],
|
||||
dst_stride_y: i32,
|
||||
dst_u: &mut [u8],
|
||||
dst_stride_u: i32,
|
||||
dst_v: &mut [u8],
|
||||
dst_stride_v: i32,
|
||||
width: i32,
|
||||
height: i32,
|
||||
) -> Result<(), ConvertError> {
|
||||
argb_assert_safety(src_argb, src_stride_argb, width, height)?;
|
||||
i420_assert_safety(
|
||||
dst_y,
|
||||
dst_stride_y,
|
||||
dst_u,
|
||||
dst_stride_u,
|
||||
dst_v,
|
||||
dst_stride_v,
|
||||
width,
|
||||
height,
|
||||
)?;
|
||||
|
||||
unsafe {
|
||||
yuv_sys::ffi::$x(
|
||||
src_argb.as_ptr(),
|
||||
src_stride_argb,
|
||||
dst_y.as_mut_ptr(),
|
||||
dst_stride_y,
|
||||
dst_u.as_mut_ptr(),
|
||||
dst_stride_u,
|
||||
dst_v.as_mut_ptr(),
|
||||
dst_stride_v,
|
||||
width,
|
||||
height,
|
||||
)
|
||||
.unwrap();
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
pub fn argb_to_rgb24(
|
||||
src_argb: &[u8],
|
||||
src_stride_argb: i32,
|
||||
dst_rgb24: &mut [u8],
|
||||
dst_stride_rgb24: i32,
|
||||
width: i32,
|
||||
height: i32,
|
||||
) -> Result<(), ConvertError> {
|
||||
argb_assert_safety(src_argb, src_stride_argb, width, height)?;
|
||||
argb_assert_safety(dst_rgb24, dst_stride_rgb24, width, height)?;
|
||||
|
||||
unsafe {
|
||||
yuv_sys::ffi::argb_to_rgb24(
|
||||
src_argb.as_ptr(),
|
||||
src_stride_argb,
|
||||
dst_rgb24.as_mut_ptr(),
|
||||
dst_stride_rgb24,
|
||||
width,
|
||||
height,
|
||||
)
|
||||
.unwrap();
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
x_to_i420!(argb_to_i420);
|
||||
x_to_i420!(abgr_to_i420);
|
||||
|
||||
i420_to_x!(i420_to_argb);
|
||||
i420_to_x!(i420_to_bgra);
|
||||
i420_to_x!(i420_to_abgr);
|
||||
i420_to_x!(i420_to_rgba);
|
||||
Reference in New Issue
Block a user