#![deny(missing_docs)]
use crate::frame::*;
use crate::serialize::{Deserialize, Serialize};
use crate::stats::EncoderStats;
use crate::util::Pixel;
use std::fmt;
use std::sync::Arc;
use thiserror::*;
#[derive(Clone, Copy, Debug)]
#[repr(C)]
pub struct Rational {
pub num: u64,
pub den: u64,
}
impl Rational {
pub const fn new(num: u64, den: u64) -> Self {
Rational { num, den }
}
pub const fn from_reciprocal(reciprocal: Self) -> Self {
Rational { num: reciprocal.den, den: reciprocal.num }
}
pub fn as_f64(self) -> f64 {
self.num as f64 / self.den as f64
}
}
#[cfg(feature = "serialize")]
impl serde::Serialize for Rational {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
S: serde::Serializer,
{
(self.num, self.den).serialize(serializer)
}
}
#[cfg(feature = "serialize")]
impl<'a> serde::Deserialize<'a> for Rational {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: serde::Deserializer<'a>,
{
let (num, den) = serde::Deserialize::deserialize(deserializer)?;
Ok(Rational::new(num, den))
}
}
#[allow(dead_code, non_camel_case_types)]
#[derive(Debug, Eq, PartialEq, Clone, Copy, Serialize, Deserialize)]
#[repr(C)]
pub enum FrameType {
KEY,
INTER,
INTRA_ONLY,
SWITCH,
}
impl FrameType {
#[inline]
pub fn has_inter(self) -> bool {
self == FrameType::INTER || self == FrameType::SWITCH
}
#[inline]
pub fn all_intra(self) -> bool {
self == FrameType::KEY || self == FrameType::INTRA_ONLY
}
}
impl fmt::Display for FrameType {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
use self::FrameType::*;
match self {
KEY => write!(f, "Key frame"),
INTER => write!(f, "Inter frame"),
INTRA_ONLY => write!(f, "Intra only frame"),
SWITCH => write!(f, "Switching frame"),
}
}
}
#[derive(Clone, Copy, Debug, Eq, PartialEq, Error)]
pub enum EncoderStatus {
#[error("need more data")]
NeedMoreData,
#[error("enough data")]
EnoughData,
#[error("limit reached")]
LimitReached,
#[error("encoded")]
Encoded,
#[error("failure")]
Failure,
#[error("not ready")]
NotReady,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct Packet<T: Pixel> {
pub data: Vec<u8>,
#[cfg_attr(feature = "serialize", serde(skip))]
pub rec: Option<Arc<Frame<T>>>,
#[cfg_attr(feature = "serialize", serde(skip))]
pub source: Option<Arc<Frame<T>>>,
pub input_frameno: u64,
pub frame_type: FrameType,
pub qp: u8,
pub enc_stats: EncoderStats,
#[cfg_attr(feature = "serialize", serde(skip))]
pub opaque: Option<Box<dyn std::any::Any + Send>>,
}
impl<T: Pixel> PartialEq for Packet<T> {
fn eq(&self, other: &Self) -> bool {
self.data == other.data
&& self.input_frameno == other.input_frameno
&& self.frame_type == other.frame_type
&& self.qp == other.qp
}
}
impl<T: Pixel> fmt::Display for Packet<T> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(
f,
"Frame {} - {} - {} bytes",
self.input_frameno,
self.frame_type,
self.data.len()
)
}
}
pub trait IntoFrame<T: Pixel> {
fn into(self) -> (Option<Arc<Frame<T>>>, Option<FrameParameters>);
}
impl<T: Pixel> IntoFrame<T> for Option<Arc<Frame<T>>> {
fn into(self) -> (Option<Arc<Frame<T>>>, Option<FrameParameters>) {
(self, None)
}
}
impl<T: Pixel> IntoFrame<T> for Arc<Frame<T>> {
fn into(self) -> (Option<Arc<Frame<T>>>, Option<FrameParameters>) {
(Some(self), None)
}
}
impl<T: Pixel> IntoFrame<T> for (Arc<Frame<T>>, FrameParameters) {
fn into(self) -> (Option<Arc<Frame<T>>>, Option<FrameParameters>) {
(Some(self.0), Some(self.1))
}
}
impl<T: Pixel> IntoFrame<T> for (Arc<Frame<T>>, Option<FrameParameters>) {
fn into(self) -> (Option<Arc<Frame<T>>>, Option<FrameParameters>) {
(Some(self.0), self.1)
}
}
impl<T: Pixel> IntoFrame<T> for Frame<T> {
fn into(self) -> (Option<Arc<Frame<T>>>, Option<FrameParameters>) {
(Some(Arc::new(self)), None)
}
}
impl<T: Pixel> IntoFrame<T> for (Frame<T>, FrameParameters) {
fn into(self) -> (Option<Arc<Frame<T>>>, Option<FrameParameters>) {
(Some(Arc::new(self.0)), Some(self.1))
}
}
impl<T: Pixel> IntoFrame<T> for (Frame<T>, Option<FrameParameters>) {
fn into(self) -> (Option<Arc<Frame<T>>>, Option<FrameParameters>) {
(Some(Arc::new(self.0)), self.1)
}
}