facett-map/tests/layerset_robot.rs
//! **Robot test for the layer-toggle Facet** (`facett_map::LayerToggles`) — the
//! Google-Maps-style "Layers" checkbox list.
//!
//! Drives the REAL egui surface through `egui_kittest`: it finds the *Buildings*
//! checkbox by its label and **clicks it** (a real AccessKit-driven click, not a
//! method call), then asserts as DATA:
//! 1. the click FLIPPED that layer's visibility in `state_json` (**red when
//! broken** — if the checkbox weren't wired, `buildings` stays `true`), and
//! 2. the shared [`LayerSet`] the facet owns now HIDES building ways from the
//! feed both map engines consume (`filter_ways` drops them) — the "hidden
//! layers aren't drawn" oracle.
//!
//! Run: `cargo test -p facett-map --test layerset_robot`
use std::cell::RefCell;
use std::rc::Rc;
use egui_kittest::Harness;
use egui_kittest::kittest::Queryable;
use facett_core::{Facet, Theme};
use facett_map::{LayerCategory, LayerToggles, Way};
/// A tiny feed with one of each toggled kind, to prove the shared filter reacts.
fn feed() -> Vec<Way> {
let th = Theme::default();
let tag = |k: &str, v: &str| vec![(k.to_string(), v.to_string())];
let ring = [(9.50, 47.10), (9.55, 47.10), (9.55, 47.15), (9.50, 47.15), (9.50, 47.10)];
vec![
Way::from_lonlat(1, &[(9.47, 47.11), (9.60, 47.15)], &tag("highway", "primary"), &th).unwrap(), // Roads
Way::from_lonlat(2, &ring, &tag("building", "yes"), &th).unwrap(), // Buildings
Way::from_lonlat(3, &ring, &tag("natural", "water"), &th).unwrap(), // Water
]
}
#[test]
fn clicking_a_checkbox_flips_the_layer_and_hides_it_from_the_feed() {
let toggles = Rc::new(RefCell::new(LayerToggles::new("Layers")));
let t2 = toggles.clone();
// Before the click: everything on, all 3 ways feed through.
let ways = feed();
assert!(toggles.borrow().is_visible(LayerCategory::Buildings), "buildings start visible");
assert_eq!(toggles.borrow().layer_set().filter_ways(&ways).len(), 3, "all layers feed through at first");
let mut harness = Harness::builder()
.with_size(egui::vec2(260.0, 420.0))
.build_ui(move |ui| {
facett_core::set_theme(ui.ctx(), Theme::default());
t2.borrow_mut().ui(ui);
});
harness.run();
// ── the ROBOT click: find the "Buildings" checkbox by label and click it ──
harness.get_by_label("Buildings").click();
harness.run();
// (1) the click flipped the layer in state_json — RED when broken.
let state = toggles.borrow().state_json();
eprintln!("[layerset_robot] state = {state}");
assert_eq!(
state["layers"]["buildings"],
serde_json::json!(false),
"clicking the Buildings checkbox turned that layer OFF in state_json"
);
assert_eq!(state["last_toggled"], serde_json::json!("buildings"), "the click landed on Buildings");
// The other layers are untouched.
assert_eq!(state["layers"]["roads"], serde_json::json!(true), "roads still on");
assert_eq!(state["layers"]["water"], serde_json::json!(true), "water still on");
// (2) the shared LayerSet now HIDES building ways from the engine feed.
let shown = toggles.borrow().layer_set().filter_ways(&ways);
assert_eq!(shown.len(), 2, "the building way is dropped from the shared feed");
assert!(
!shown.iter().any(|w| w.style.kind == facett_map::WayKind::Building),
"no building survives once its layer is toggled off"
);
#[cfg(feature = "testmatrix")]
facett_core::testmatrix::emit(
"facett-map.layerset_robot",
"checkbox_toggle_hides_layer",
state["layers"]["buildings"] == serde_json::json!(false) && shown.len() == 2,
&format!("clicked Buildings → off; feed 3 → {} ways", shown.len()),
);
}