blob: 979be7cf4cb2a370b272081b8b8bfad949c97740 [file] [log] [blame]
use anyhow::anyhow;
use egui::{Button, RichText, Ui};
use egui_extras::{Column, TableBuilder};
use log::warn;
use crate::views::stats_viewer::create_file_download;
use crate::{app_state::AppState, stream::CurrentFrame};
use crate::views::{RenderView, SelectedObject};
use super::SelectedObjectKind;
pub struct BlockInfoViewer;
// TODO(comc): Click on a MV to load the corresponding frame and block.
impl RenderView for BlockInfoViewer {
fn title(&self) -> String {
"Block Info".into()
}
fn render(&self, ui: &mut Ui, state: &mut AppState) -> anyhow::Result<()> {
let Some(frame) = state.stream.current_frame() else {
// No frame loaded yet.
return Ok(());
};
let Some(SelectedObject {
kind: selected_object_kind,
..
}) = &state.settings.selected_object
else {
// Nothing is selected.
return Ok(());
};
let selected_object_kind = selected_object_kind.clone();
let is_transform_unit = matches!(selected_object_kind, SelectedObjectKind::TransformUnit(_));
let is_superblock = matches!(selected_object_kind, SelectedObjectKind::Superblock(_));
if ui.add_enabled(!is_superblock, Button::new("Go to parent")).clicked() {
if let Some(parent) = selected_object_kind.get_parent(frame) {
state.settings.selected_object = Some(SelectedObject::new(parent));
}
}
ui.end_row();
if ui.button("Show pixels for current block").clicked() {
state.settings.sharable.show_pixel_viewer = true;
}
ui.end_row();
if let SelectedObjectKind::CodingUnit(cu) = selected_object_kind {
let ctx = cu.try_resolve(frame).ok_or(anyhow!("Invalid coding unit index"))?;
if ui.button("Dump current block as JSON").clicked() {
if let Some(stream) = &state.stream {
let Some(rect) = selected_object_kind.rect(frame) else {
return Err(anyhow!("Invalid coding unit index"));
};
let file_name = format!(
"{}_frame_{:04}_block_{}x{}_x{}_y{}.json",
stream.stream_info.stream_name,
stream.current_frame_index,
rect.width() as i32,
rect.height() as i32,
rect.left_top().x as i32,
rect.left_top().y as i32,
);
let data = serde_json::to_string_pretty(ctx.coding_unit).unwrap();
if let Err(err) = create_file_download(data.as_bytes(), &file_name) {
warn!("Failed to create file download: {err:?}");
}
}
}
}
// TODO(comc): Grey out instead of removing?
if is_transform_unit && ui.button("Show transform coeffs").clicked() {
state.settings.sharable.show_coeffs_viewer = true;
}
ui.separator();
let Ok(info) = state
.settings
.selected_object
.as_mut()
.unwrap()
.get_or_calculate_info(frame)
else {
return Ok(());
};
TableBuilder::new(ui)
.column(Column::initial(300.0).resizable(true))
.column(Column::remainder())
.striped(true)
.header(20.0, |mut header| {
header.col(|ui| {
ui.label(RichText::new("Property").strong());
});
header.col(|ui| {
ui.label(RichText::new("Value").strong());
});
})
.body(|mut body| {
for field in info.fields.iter() {
body.row(20.0, |mut row| {
row.col(|col| {
col.label(&field.name);
});
row.col(|col| {
col.label(&field.value);
});
});
}
});
Ok(())
}
}