feat(player): add chunk/scene markers on progress bar

This commit is contained in:
accusys
2026-03-19 01:54:12 +08:00
parent dbcd7ba5e9
commit 722af4fe87
16 changed files with 137 additions and 11 deletions

View File

@@ -15,7 +15,7 @@ mod player;
mod web;
use config::Config;
use overlay::{AsrLoader, YoloLoader};
use overlay::{AsrLoader, ChunkLoader, YoloLoader};
use player::ffmpeg::FFmpegDecoder;
use player::state::{PlaybackState, PlayerState};
@@ -63,6 +63,7 @@ fn run(config: &Config) -> Result<()> {
let mut video_info = None;
let mut asr: Option<AsrLoader> = None;
let mut yolo: Option<YoloLoader> = None;
let mut chunks: Option<ChunkLoader> = None;
let mut is_fullscreen = false;
if let Some(ref video_path) = config.video {
@@ -111,6 +112,19 @@ fn run(config: &Config) -> Result<()> {
}
}
if let Some(ref chunks_path) = config.chunks {
info!("Loading Chunks: {:?}", chunks_path);
match ChunkLoader::load(Path::new(chunks_path)) {
Ok(loader) => {
info!("Chunks loaded: {} scenes", loader.scene_count());
chunks = Some(loader);
}
Err(e) => {
error!("Failed to load Chunks: {}", e);
}
}
}
let mut player_state = PlayerState::default();
if let Some(ref info) = video_info {
player_state.total_frames = info.frame_count;
@@ -510,6 +524,58 @@ fn run(config: &Config) -> Result<()> {
progress_width,
progress_bar_height as u32,
));
if player_state.show_chunks {
if let Some(ref chunk_loader) = chunks {
let bar_start = 10i32;
let bar_width = config.width as i32 - 20;
let boundaries = chunk_loader.get_scene_boundaries();
for &boundary_frame in &boundaries {
let ratio = boundary_frame as f64 / player_state.total_frames as f64;
let x_pos = (bar_start + (bar_width as f64 * ratio) as i32)
.min(bar_start + bar_width - 1);
if x_pos > bar_start && x_pos < bar_start + bar_width {
canvas.set_draw_color(sdl2::pixels::Color::RGB(255, 200, 50));
let _ = canvas.fill_rect(Rect::new(
x_pos,
progress_y - 2,
2,
(progress_bar_height + 4) as u32,
));
}
}
if let Some(current_scene) =
chunk_loader.get_current_scene(player_state.current_frame)
{
if let Some(ref font) = font {
let scene_text = format!("Scene {}", current_scene.scene_number);
if let Ok(surface) = font
.render(&scene_text)
.solid(sdl2::pixels::Color::RGB(255, 200, 50))
{
if let Ok(tex) =
texture_creator.create_texture_from_surface(&surface)
{
let rect = Rect::new(
bar_start + bar_width - surface.width() as i32 - 10,
progress_y - 25,
surface.width(),
surface.height(),
);
canvas.set_draw_color(sdl2::pixels::Color::RGBA(0, 0, 0, 180));
let _ = canvas.fill_rect(Rect::new(
rect.x() - 4,
rect.y() - 2,
rect.width() + 8,
rect.height() + 4,
));
canvas.copy(&tex, None, Some(rect)).ok();
}
}
}
}
}
}
}
canvas.present();