//! Where a frame puts things, with no window to put them in. use iris::harness::{Harness, assert_corners}; use iris::prelude::*; /// A fixed 100 wide, and the rest of the 400 to its neighbour. fn two_rects(h: &mut Harness) -> (WidgetId, WidgetId) { let left = rect(Color::RED).width(100).add(&mut h.rsc); let right = rect(Color::BLUE).add(&mut h.rsc); h.set_root((left, right).span(Dir::RIGHT)); (left.id(), right.id()) } #[test] fn a_span_gives_each_child_the_width_it_asked_for() { let mut h = Harness::new((400, 200)); let (left, right) = two_rects(&mut h); assert_corners!(h, left, (0, 0), (100, 200)); assert_corners!(h, right, (100, 0), (400, 200)); } #[test] fn resizing_relays_out_against_the_new_output() { let mut h = Harness::new((400, 200)); let (left, right) = two_rects(&mut h); h.resize((800, 100)); assert!(h.needs_redraw()); h.frame(); assert_corners!(h, left, (0, 0), (100, 100)); assert_corners!(h, right, (100, 0), (800, 100)); } #[test] fn an_empty_widget_takes_a_share_of_a_span() { let mut h = Harness::new((400, 200)); let gap = ().add(&mut h.rsc); let right = rect(Color::BLUE).width(100).add(&mut h.rsc); h.set_root((gap, right).span(Dir::RIGHT)); assert_corners!(h, gap, (0, 0), (300, 200)); assert_corners!(h, right, (300, 0), (400, 200)); } #[test] fn a_child_drawn_twice_moves_once() { let mut h = Harness::new((400, 200)); // `Aligned` draws its child twice; listing it twice would move it twice. let inner = rect(Color::BLUE).add(&mut h.rsc); let centered = inner.center().width(200).add(&mut h.rsc); let left = rect(Color::RED).width(100).add(&mut h.rsc); h.set_root((left, centered).span(Dir::RIGHT)); assert_corners!(h, inner, (100, 0), (300, 200)); h.rsc[left].x = Some(Len::abs(150)); h.frame(); assert_corners!(h, inner, (150, 0), (350, 200)); } #[test] fn a_resize_lands_where_a_cold_start_would() { let build = |h: &mut Harness| { let para = wtext( "Wrapping shapes one source into as many lines as its container leaves room \ for, so the height of a paragraph is an answer rather than a setting.", ) .size(20) .wrap(true) .pad(16) .add(&mut h.rsc); let below = rect(Color::RED).add(&mut h.rsc); let root = (para, below).span(Dir::DOWN).pad(12); h.set_root(root); (para, below) }; let mut cold = Harness::new((900, 1200)); let (cold_para, cold_below) = build(&mut cold); let mut resized = Harness::new((1920, 1200)); let (para, below) = build(&mut resized); resized.resize((900, 1200)); resized.frame(); assert_eq!(resized.region(¶), cold.region(&cold_para), "paragraph"); assert_eq!(resized.region(&below), cold.region(&cold_below), "below"); } #[test] fn a_fixed_box_is_drawn_again_rather_than_stretched() { let mut h = Harness::new((400, 400)); // The panel fills a stack sized by its sibling, so it is drawn in the // whole box and then placed in the shorter one. Reusing it in that fixed // box afterwards would leave it whatever height it happened to have. let panel = rect(Color::BLUE).add(&mut h.rsc); let leaf = rect(Color::RED).height(100).add(&mut h.rsc); let stack = (panel, leaf) .stack() .size(StackSize::Child(1)) .add(&mut h.rsc); h.set_root(stack.align(Align::TOP)); assert_corners!(h, panel, (0, 0), (400, 100)); h.rsc[leaf].y = Some(Len::abs(250)); h.frame(); assert_corners!(h, panel, (0, 0), (400, 250)); } #[test] fn a_moved_subtree_takes_its_children_with_it() { let mut h = Harness::new((400, 400)); let first = rect(Color::RED).height(40).add(&mut h.rsc); let inner = rect(Color::BLUE).add(&mut h.rsc); let row = inner.pad(10).height(40).add(&mut h.rsc); h.set_root((first, row).span(Dir::DOWN)); assert_corners!(h, inner, (10, 50), (390, 70)); h.rsc[first].y = Some(Len::abs(80)); h.frame(); // The row is the same shape somewhere else, so one slot moved it and // `inner`'s own region was never rewritten. assert_corners!(h, inner, (10, 90), (390, 110)); }