From 549511e9deafd9ec08b3c80489e7e85c5f5f0b3b Mon Sep 17 00:00:00 2001 From: Kostya Shishkov Date: Mon, 2 Oct 2023 19:42:39 +0200 Subject: [PATCH] videoplayer: allow custom scaling --- videoplayer/src/main.rs | 70 ++++++++++++++++++++++++++++++++++++++--- 1 file changed, 66 insertions(+), 4 deletions(-) diff --git a/videoplayer/src/main.rs b/videoplayer/src/main.rs index e695280..cd35eb5 100644 --- a/videoplayer/src/main.rs +++ b/videoplayer/src/main.rs @@ -92,6 +92,41 @@ macro_rules! debug_log { ($log: expr; $blk: block) => {}; } +enum ScaleSize { + Auto, + Times(f32), + Fixed(usize, usize) +} + +impl FromStr for ScaleSize { + type Err = (); + fn from_str(s: &str) -> Result { + if matches!(s, "" | "auto") { + Ok(ScaleSize::Auto) + } else if s.ends_with('x') || s.ends_with('X') { + let factor = s[..s.len() - 1].parse::().map_err(|_| ())?; + if factor > 0.0 { + Ok(ScaleSize::Times(factor)) + } else { + Err(()) + } + } else if s.contains('x') | s.contains('X') { + let mut dims = if s.contains('x') { s.split('x') } else { s.split('X') }; + let w = dims.next().unwrap(); + let h = dims.next().unwrap(); + let width = w.parse::().map_err(|_| ())?; + let height = h.parse::().map_err(|_| ())?; + if width > 0 && height > 0 { + Ok(ScaleSize::Fixed(width, height)) + } else { + Err(()) + } + } else { + Err(()) + } + } +} + pub enum PktSendEvent { Packet(NAPacket), GetFrames, @@ -303,6 +338,7 @@ struct Player { has_audio: bool, video_str: u32, audio_str: u32, + sc_size: ScaleSize, vthreads: usize, use_mt: bool, @@ -340,6 +376,7 @@ impl Player { has_audio: false, video_str: 0, audio_str: 0, + sc_size: ScaleSize::Auto, vthreads: 3, use_mt: true, @@ -707,10 +744,26 @@ impl Player { return window; } - while (width <= 384) && (height <= 288) { - width <<= 1; - height <<= 1; - } + match self.sc_size { + ScaleSize::Auto => { + while (width <= 384) && (height <= 288) { + width <<= 1; + height <<= 1; + } + }, + ScaleSize::Times(factor) => { + let nw = ((width as f32) * factor).ceil() as usize; + let nh = ((height as f32) * factor).ceil() as usize; + if nw > 0 && nh > 0 { + width = nw; + height = nh; + } + }, + ScaleSize::Fixed(w, h) => { + width = w; + height = h; + }, + }; // prepare playback structure let mut new_vcontrol = VideoControl::new(video_dec, width, height, tb_num, tb_den); @@ -927,6 +980,15 @@ fn main() { } } }, + "-scale" => { + if let Some(arg) = aiter.next() { + if let Ok(ssize) = arg.parse::() { + player.sc_size = ssize; + } else { + println!("invalid scale size"); + } + } + }, _ => { window = player.play(window, arg, seek_time); if player.end { break; } -- 2.30.2