scrolling window centered

This commit is contained in:
2026-02-13 23:00:23 -06:00
parent e3f312ac52
commit b5a0790cb6

View File

@@ -298,9 +298,34 @@ fn ui(frame: &mut Frame, app: &App) {
); );
} }
fn compute_window(len: usize, selected: usize, viewport: usize) -> (usize, usize) {
if len == 0 || viewport == 0 {
return (0, 0);
}
let viewport = viewport.min(len);
let half = viewport / 2;
let mut start = selected.saturating_sub(half);
if start + viewport > len {
start = len - viewport;
}
let end = start + viewport;
(start, end)
}
fn render_categories(frame: &mut Frame, app: &App, left: Rect, right: Rect) { fn render_categories(frame: &mut Frame, app: &App, left: Rect, right: Rect) {
let items: Vec<ListItem> = app // how many rows can we show inside the bordered block?
.items let viewport = left.height.saturating_sub(2) as usize;
let len = app.items.len();
let selected = app.selected.min(len.saturating_sub(1));
let (start, end) = compute_window(len, selected, viewport);
let items: Vec<ListItem> = app.items[start..end]
.iter() .iter()
.map(|s| ListItem::new(s.as_str())) .map(|s| ListItem::new(s.as_str()))
.collect(); .collect();
@@ -311,11 +336,17 @@ fn render_categories(frame: &mut Frame, app: &App, left: Rect, right: Rect) {
.highlight_style(Style::default().add_modifier(Modifier::REVERSED)); .highlight_style(Style::default().add_modifier(Modifier::REVERSED));
let mut state = ListState::default(); let mut state = ListState::default();
state.select(Some(app.selected)); state.select(Some(selected - start)); // selection relative to slice
frame.render_stateful_widget(list, left, &mut state); frame.render_stateful_widget(list, left, &mut state);
let detail = format!("Details for:\n\n{}", app.items[app.selected]); // Right pane details (use the real selected item)
let detail = if len > 0 {
format!("Details for:\n\n{}", app.items[selected])
} else {
"No items".to_string()
};
frame.render_widget( frame.render_widget(
Paragraph::new(detail) Paragraph::new(detail)
.block(Block::bordered().title("Details").merge_borders(MergeStrategy::Exact)), .block(Block::bordered().title("Details").merge_borders(MergeStrategy::Exact)),