clean break video code into new module

This commit is contained in:
Lily Tsuru 2024-09-09 22:02:57 -04:00
parent a6734667de
commit fa929641e5
4 changed files with 26 additions and 17 deletions

View file

@ -1,9 +1,11 @@
mod encoder_thread;
mod ffmpeg;
mod video;
mod surface;
mod types;
mod vnc_engine;
use video::encoder_thread;
use video::ffmpeg;
use std::{
sync::{Arc, Mutex},
time::Duration,
@ -62,8 +64,8 @@ async fn main() -> anyhow::Result<()> {
let (engine_input_tx, engine_input_rx) = mpsc::channel(16);
// H.264 encoder related
let frame: Arc<Mutex<Option<ffmpeg_the_third::frame::Video>>> = Arc::new(Mutex::new(None));
let (mut encoder_rx, encoder_tx) = encoder_thread::encoder_thread_spawn(&frame);
let frame: Arc<Mutex<Option<ffmpeg::frame::Video>>> = Arc::new(Mutex::new(None));
let (mut encoder_rx, encoder_tx) = video::encoder_thread_spawn(&frame);
let state = Arc::new(AppState::new(engine_input_tx, encoder_tx));

View file

@ -4,6 +4,9 @@ use std::{
};
use tokio::sync::mpsc::{self, error::TryRecvError};
use super::ffmpeg;
use super::h264_encoder_sw::H264EncoderSW;
pub enum EncodeThreadInput {
Init { size: crate::types::Size },
ForceKeyframe,
@ -12,20 +15,18 @@ pub enum EncodeThreadInput {
#[derive(Clone)]
pub enum EncodeThreadOutput {
Frame { packet: ffmpeg_the_third::Packet },
Frame { packet: ffmpeg::Packet },
}
#[inline]
fn set_frame_flags(frame: &mut ffmpeg_the_third::Frame, force_keyframe: bool) {
unsafe {
if force_keyframe {
(*frame.as_mut_ptr()).pict_type =
ffmpeg_the_third::sys::AVPictureType::AV_PICTURE_TYPE_I;
(*frame.as_mut_ptr()).pict_type = ffmpeg::sys::AVPictureType::AV_PICTURE_TYPE_I;
(*frame.as_mut_ptr()).flags = ffmpeg_the_third::sys::AV_FRAME_FLAG_KEY;
(*frame.as_mut_ptr()).key_frame = 1;
} else {
(*frame.as_mut_ptr()).pict_type =
ffmpeg_the_third::sys::AVPictureType::AV_PICTURE_TYPE_NONE;
(*frame.as_mut_ptr()).pict_type = ffmpeg::sys::AVPictureType::AV_PICTURE_TYPE_NONE;
(*frame.as_mut_ptr()).flags = 0i32;
(*frame.as_mut_ptr()).key_frame = 0;
}
@ -35,11 +36,11 @@ fn set_frame_flags(frame: &mut ffmpeg_the_third::Frame, force_keyframe: bool) {
fn encoder_thread_main(
mut rx: mpsc::Receiver<EncodeThreadInput>,
tx: mpsc::Sender<EncodeThreadOutput>,
frame: &Arc<Mutex<Option<ffmpeg_the_third::frame::Video>>>,
frame: &Arc<Mutex<Option<ffmpeg::frame::Video>>>,
) {
let mut packet = ffmpeg_the_third::Packet::empty();
let mut packet = ffmpeg::Packet::empty();
let mut encoder: Option<crate::ffmpeg::H264Encoder> = None;
let mut encoder: Option<H264EncoderSW> = None;
let mut sws = None;
let mut yuv_frame = None;
@ -73,7 +74,7 @@ fn encoder_thread_main(
);
encoder = Some(
crate::ffmpeg::H264Encoder::new(size, 60, 3 * (1000 * 1000))
H264EncoderSW::new(size, 60, 3 * (1000 * 1000))
.expect("Failed to create encoder"),
);
}

View file

@ -1,6 +1,6 @@
use super::ffmpeg;
use anyhow::Context;
use ffmpeg::error::EAGAIN;
use ffmpeg_the_third as ffmpeg;
use ffmpeg::codec as lavc; // lavc
@ -19,12 +19,12 @@ pub fn create_context_from_codec(codec: ffmpeg::Codec) -> Result<lavc::Context,
}
}
/// A simple H.264 encoder.
pub struct H264Encoder {
/// A simple software H.264 encoder.
pub struct H264EncoderSW {
encoder: ffmpeg::encoder::video::Encoder,
}
impl H264Encoder {
impl H264EncoderSW {
pub fn new(size: Size, max_framerate: u32, bitrate: usize) -> anyhow::Result<Self> {
let encoder = ffmpeg::encoder::find(lavc::Id::H264).expect("could not find libx264");

6
server/src/video/mod.rs Normal file
View file

@ -0,0 +1,6 @@
pub mod h264_encoder_sw;
pub mod encoder_thread;
pub use ffmpeg_the_third as ffmpeg;
pub use encoder_thread::*;