From a2e4b2b1da6d70844f0e2a0f53397b79beedc2a9 Mon Sep 17 00:00:00 2001 From: dotCooCoo Date: Sat, 24 Oct 2026 15:48:55 -0700 Subject: [PATCH] Error Checking: the Circular References submenu scrolls The submenu lists up to 100 cells. When the list was taller than the window, the cells below its bottom edge could not be reached. The list now sits in a scroll area 400 points high. --- crates/ui-egui/src/ribbon.rs | 12 ++++---- .../ui-egui/tests/it/error_checking_menu.rs | 28 +++++++++++++++++++ 2 files changed, 35 insertions(+), 5 deletions(-) diff --git a/crates/ui-egui/src/ribbon.rs b/crates/ui-egui/src/ribbon.rs index 85f5b81cf..04c0e814e 100644 --- a/crates/ui-egui/src/ribbon.rs +++ b/crates/ui-egui/src/ribbon.rs @@ -2039,12 +2039,14 @@ fn formulas(app: &mut SheetApp, ui: &mut Ui) { let circular = circular_references(app); ui.add_enabled_ui(!circular.is_empty(), |ui| { ui.menu_button(lang.tr("Circular References"), |ui| { - for (sheet, cell, label) in circular { - if ui.button(label).clicked() { - act(app, "selection.set", json!({"range": cell, "sheet": sheet})); - app.grid.ensure_visible = true; + egui::ScrollArea::vertical().id_salt("circular_references").max_height(400.0).show(ui, |ui| { + for (sheet, cell, label) in circular { + if ui.button(label).clicked() { + act(app, "selection.set", json!({"range": cell, "sheet": sheet})); + app.grid.ensure_visible = true; + } } - } + }); }); }); }); diff --git a/crates/ui-egui/tests/it/error_checking_menu.rs b/crates/ui-egui/tests/it/error_checking_menu.rs index 0639020da..10467e163 100644 --- a/crates/ui-egui/tests/it/error_checking_menu.rs +++ b/crates/ui-egui/tests/it/error_checking_menu.rs @@ -127,3 +127,31 @@ fn circular_references_scrolls_to_the_cell_picked() { assert_eq!(h.state().session.active().unwrap().selection.active.a1(), "C500"); assert!(h.state().view().scroll.y > 0.0, "the grid scrolls to the cell picked"); } + +#[test] +fn circular_references_scrolls_a_list_taller_than_the_window() { + let mut h = harness(false); + for row in 1..=100 { + h.state_mut().run("cell.set", json!({"cell": format!("A{row}"), "input": format!("=A{row}+1")})).unwrap(); + } + h.state_mut().run("selection.set", json!({"range": "H20"})).unwrap(); + h.run_steps(4); + open_menu(&mut h); + hover(&mut h, CIRCULAR); + let window = h.ctx.content_rect(); + assert!(h.get_by_label("Sheet1!A100").rect().bottom() > window.bottom(), "setup: the last cell starts below the window"); + hover(&mut h, "Sheet1!A1"); + for _ in 0..20 { + h.input_mut().events.push(Event::MouseWheel { + unit: egui::MouseWheelUnit::Line, + delta: vec2(0.0, -10.0), + phase: egui::TouchPhase::Move, + modifiers: egui::Modifiers::NONE, + }); + h.run_steps(4); + } + let last = h.get_by_label("Sheet1!A100").rect(); + assert!(last.bottom() <= window.bottom(), "the wheel brings the last cell into the window: {last:?} in {window:?}"); + click(&mut h, last.center()); + assert_eq!(h.state().session.active().unwrap().selection.active.a1(), "A100"); +}