Fix header label overlap in narrow windows (#130)

This commit is contained in:
Osman Said authored and GitHub committed 2026-10-12 01:53:50 -04:00
1 parent 0358cda174
commit e49bdc94dc
3 files changed
+85 -7

No files matched your search

+14 -5
View File
@@ -80,11 +80,6 @@ impl LauncherUi {
let logo = vec2(14.0 * crate::icons::ARTCRAFT_LOGO_ASPECT, 14.0);
let (cell, _) = ui.allocate_exact_size(vec2(logo.x + 40.0, h), Sense::hover());
egui::Image::new(crate::icons::artcraft_logo(t.dark)).alt_text(tl!("ArtCraft")).paint_at(ui, Rect::from_center_size(cell.center(), logo));
widgets::rule(ui, h);
ui.add_space(16.0);
widgets::tag(ui, tl!("Launcher"), t.invert_bg, t.invert_fg);
ui.add_space(12.0);
widgets::hud(ui, tl!("Craft App Suite"), t.muted);
ui.with_layout(egui::Layout::right_to_left(egui::Align::Center), |ui| {
if bar == TitleBar::Custom {
widgets::window_buttons(ui, h);
@@ -112,6 +107,20 @@ impl LauncherUi {
}
ui.add_space(6.0);
widgets::rule(ui, h);
// The controls reserve their actual widths before the secondary text gets space.
ui.with_layout(egui::Layout::left_to_right(egui::Align::Center), |ui| {
let tag_width =
widgets::caps(ui, tl!("Launcher"), theme::HUD_SIZE, theme::mono_bold(), theme::HUD_SPACING, t.ink).size().x + 16.0;
if ui.available_width() >= 17.0 + tag_width {
widgets::rule(ui, h);
ui.add_space(16.0);
widgets::tag(ui, tl!("Launcher"), t.invert_bg, t.invert_fg);
}
if ui.available_width() >= 12.0 + widgets::hud_galley(ui, tl!("Craft App Suite"), t.muted).size().x {
ui.add_space(12.0);
widgets::hud(ui, tl!("Craft App Suite"), t.muted);
}
});
});
});
}
+13
View File
@@ -184,4 +184,17 @@ fn german_switches_persists_and_keeps_install_actions() {
let (mut web, _) = harness_language(ViewMode::Grid, egui::Theme::Dark, false, &restored.language);
web.run_steps(6);
assert!(web.query_all_by_label("Für macOS herunterladen").count() >= 3);
for width in [720.0, 800.0, 1180.0] {
web.set_size(egui::vec2(width, 900.0));
web.run_steps(6);
for label in ["Grid", "Table", "Settings", "Check for updates"] {
let rect = web.get_by_label(artcraft_launcher_ui_egui::i18n::t(label)).rect();
assert!(rect.left() >= 0.0 && rect.right() <= width, "{width}: {label} {rect:?}");
for label in ["Launcher", "Craft App Suite"] {
if let Some(text) = web.query_by_label(label) {
assert!(!rect.intersects(text.rect()), "{width}: {label} overlaps {rect:?}");
}
}
}
}
}
+58 -2
View File
@@ -123,6 +123,23 @@ fn harness_with(
manage: bool,
scale: f32,
) -> (Harness<'static, Option<LauncherUi>>, Rc<RefCell<Vec<Command>>>) {
harness_with_title_bar(events, view, theme, manage, scale, artcraft_launcher_ui_egui::TitleBar::Native)
}
fn harness_with_title_bar(
events: Vec<Event>,
view: ViewMode,
theme: egui::Theme,
manage: bool,
scale: f32,
bar: artcraft_launcher_ui_egui::TitleBar,
) -> (Harness<'static, Option<LauncherUi>>, Rc<RefCell<Vec<Command>>>) {
struct HeaderHost(artcraft_launcher_ui_egui::TitleBar);
impl Host for HeaderHost {
fn title_bar(&self) -> artcraft_launcher_ui_egui::TitleBar {
self.0
}
}
// Integration tests compile without cfg!(test), so system_lang() picks up the
// developer's locale. Force English so labels match the assertions.
artcraft_launcher_ui_egui::i18n::set_test_lang(artcraft_launcher_ui_egui::i18n::Lang::EN);
@@ -146,8 +163,8 @@ fn harness_with(
*state = Some(LauncherUi::new(ui.ctx(), Box::new(b), s));
}
if let Some(l) = state.as_mut() {
l.logic(&ui.ctx().clone(), &mut NoHost);
l.ui(ui, &mut NoHost);
l.logic(&ui.ctx().clone(), &mut HeaderHost(bar));
l.ui(ui, &mut HeaderHost(bar));
}
},
None,
@@ -933,3 +950,42 @@ fn the_rate_limit_notice_never_runs_under_the_footer_links() {
}
}
}
#[test]
fn narrow_header_keeps_the_view_switch_clear_of_brand_text() {
use artcraft_launcher_ui_egui::TitleBar;
for theme in [egui::Theme::Dark, egui::Theme::Light] {
for bar in [TitleBar::Native, TitleBar::MacOs, TitleBar::Custom] {
let (mut h, _) = harness_with_title_bar(events(), ViewMode::Grid, theme, true, 1.0, bar);
for width in (720..=1180).step_by(10).chain([720, 1180]).map(|w| w as f32) {
h.set_size(egui::vec2(width, 900.0));
h.run_steps(6);
for label in ["Grid", "Table", "Settings", "Check for updates"] {
let rect = h.get_by_label(label).rect();
assert!(rect.left() >= 0.0 && rect.right() <= width, "{bar:?} {width}: {label} {rect:?}");
for label in ["Launcher", "Craft App Suite"] {
if let Some(text) = h.query_by_label(label) {
assert!(!rect.intersects(text.rect()), "{bar:?} {width}: {label} overlaps {rect:?}");
}
}
}
if bar == TitleBar::Custom {
for label in ["Minimize", "Maximize", "Close"] {
let rect = h.get_by_label(label).rect();
assert!(rect.left() >= 0.0 && rect.right() <= width, "{width}: {label} {rect:?}");
}
}
if width == 1180.0 {
h.get_by_label("Launcher");
h.get_by_label("Craft App Suite");
}
if [720.0, 800.0, 1180.0].contains(&width) {
snapshot(&mut h, &format!("header-{theme:?}-{bar:?}-{width}"));
}
}
h.get_by_label("Table").click();
h.run_steps(2);
assert_eq!(h.state().as_ref().unwrap().settings.view, ViewMode::Table);
}
}
}