From d929a4344fc593488aaacbc4b597d962d0405889 Mon Sep 17 00:00:00 2001 From: Nicola Papale Date: Mon, 6 Nov 2023 21:15:27 +0100 Subject: [PATCH 01/45] Add a gizmo-based overlay to show UI node outlines --- Cargo.toml | 3 + crates/bevy_internal/Cargo.toml | 3 + crates/bevy_ui/Cargo.toml | 12 +- crates/bevy_ui/src/debug_overlay/inset.rs | 189 +++++++++++++++++ crates/bevy_ui/src/debug_overlay/mod.rs | 247 ++++++++++++++++++++++ crates/bevy_ui/src/lib.rs | 5 + 6 files changed, 455 insertions(+), 4 deletions(-) create mode 100644 crates/bevy_ui/src/debug_overlay/inset.rs create mode 100644 crates/bevy_ui/src/debug_overlay/mod.rs diff --git a/Cargo.toml b/Cargo.toml index 70e9a4ca7cb15..dbbc69f3c433d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -112,6 +112,9 @@ bevy_ui = [ "bevy_sprite", ] +# Enable the bevy_ui debug overlay +bevy_ui_debug = ["bevy_internal/bevy_ui_debug"] + # winit window and input backend bevy_winit = ["bevy_internal/bevy_winit"] diff --git a/crates/bevy_internal/Cargo.toml b/crates/bevy_internal/Cargo.toml index a9c46dd06a615..cf47f8b42954b 100644 --- a/crates/bevy_internal/Cargo.toml +++ b/crates/bevy_internal/Cargo.toml @@ -118,6 +118,9 @@ file_watcher = ["bevy_asset?/file_watcher"] # Enables watching embedded files for Bevy Asset hot-reloading embedded_watcher = ["bevy_asset?/embedded_watcher"] +# Enable the bevy_ui debug overlay +bevy_ui_debug = ["bevy_ui?/debug"] + [dependencies] # bevy bevy_a11y = { path = "../bevy_a11y", version = "0.12.0" } diff --git a/crates/bevy_ui/Cargo.toml b/crates/bevy_ui/Cargo.toml index b6dd346f955ec..5ba089af35f22 100644 --- a/crates/bevy_ui/Cargo.toml +++ b/crates/bevy_ui/Cargo.toml @@ -8,27 +8,31 @@ repository = "https://github.com/bevyengine/bevy" license = "MIT OR Apache-2.0" keywords = ["bevy"] +[features] +default = [] +debug = ["bevy_gizmos", "bevy_core"] + [dependencies] # bevy bevy_a11y = { path = "../bevy_a11y", version = "0.12.0" } bevy_app = { path = "../bevy_app", version = "0.12.0" } bevy_asset = { path = "../bevy_asset", version = "0.12.0" } +bevy_core = { path = "../bevy_core", version = "0.12.0", optional = true } bevy_core_pipeline = { path = "../bevy_core_pipeline", version = "0.12.0" } bevy_derive = { path = "../bevy_derive", version = "0.12.0" } bevy_ecs = { path = "../bevy_ecs", version = "0.12.0" } +bevy_gizmos = { path = "../bevy_gizmos", version = "0.12.0", optional = true } bevy_hierarchy = { path = "../bevy_hierarchy", version = "0.12.0" } bevy_input = { path = "../bevy_input", version = "0.12.0" } bevy_log = { path = "../bevy_log", version = "0.12.0" } bevy_math = { path = "../bevy_math", version = "0.12.0" } -bevy_reflect = { path = "../bevy_reflect", version = "0.12.0", features = [ - "bevy", -] } +bevy_reflect = { path = "../bevy_reflect", version = "0.12.0", features = ["bevy"] } bevy_render = { path = "../bevy_render", version = "0.12.0" } bevy_sprite = { path = "../bevy_sprite", version = "0.12.0" } bevy_text = { path = "../bevy_text", version = "0.12.0", optional = true } bevy_transform = { path = "../bevy_transform", version = "0.12.0" } -bevy_window = { path = "../bevy_window", version = "0.12.0" } bevy_utils = { path = "../bevy_utils", version = "0.12.0" } +bevy_window = { path = "../bevy_window", version = "0.12.0" } # other taffy = { version = "0.3.10" } diff --git a/crates/bevy_ui/src/debug_overlay/inset.rs b/crates/bevy_ui/src/debug_overlay/inset.rs new file mode 100644 index 0000000000000..276bcfd639f1d --- /dev/null +++ b/crates/bevy_ui/src/debug_overlay/inset.rs @@ -0,0 +1,189 @@ +use bevy_gizmos::prelude::Gizmos; +use bevy_math::{Vec2, Vec2Swizzles}; +use bevy_render::prelude::Color; +use bevy_transform::prelude::GlobalTransform; +use bevy_utils::HashMap; + +use super::{CameraQuery, LayoutRect}; + +trait ApproxF32 { + fn is(self, other: f32) -> bool; +} +impl ApproxF32 for f32 { + fn is(self, other: f32) -> bool { + let diff = (self - other).abs(); + diff < 0.001 + } +} + +fn rect_border_axis(rect: LayoutRect) -> (f32, f32, f32, f32) { + let pos = rect.pos; + let size = rect.size; + let offset = pos + size; + (pos.x, offset.x, pos.y, offset.y) +} + +#[derive(PartialEq, Eq, PartialOrd, Ord, Clone, Copy, Debug)] +enum Dir { + Start, + End, +} +impl Dir { + const fn increments(self) -> i64 { + match self { + Dir::Start => 1, + Dir::End => -1, + } + } +} +impl From for Dir { + fn from(value: i64) -> Self { + if value.is_positive() { + Dir::Start + } else { + Dir::End + } + } +} +/// Collection of axis aligned "lines" (actually just their coordinate on +/// a given axis). +#[derive(Debug, Clone)] +struct DrawnLines { + lines: HashMap, + width: f32, +} +#[allow(clippy::cast_precision_loss, clippy::cast_possible_truncation)] +impl DrawnLines { + fn new(width: f32) -> Self { + DrawnLines { + lines: HashMap::new(), + width, + } + } + /// Return `value` offset by as many `increment`s as necessary to make it + /// not overlap with already drawn lines. + fn inset(&self, value: f32) -> f32 { + let scaled = value / self.width; + let fract = scaled.fract(); + let mut on_grid = scaled.floor() as i64; + for _ in 0..10 { + let Some(dir) = self.lines.get(&on_grid) else { + break; + }; + // TODO(clean): This fixes a panic, but I'm not sure how valid this is + let Some(added) = on_grid.checked_add(dir.increments()) else { + break; + }; + on_grid = added; + } + ((on_grid as f32) + fract) * self.width + } + /// Remove a line from the collection of drawn lines. + /// + /// Typically, we only care for pre-existing lines when drawing the children + /// of a container, nothing more. So we remove it after we are done with + /// the children. + fn remove(&mut self, value: f32, increment: i64) { + let mut on_grid = (value / self.width).floor() as i64; + loop { + // TODO(clean): This fixes a panic, but I'm not sure how valid this is + let Some(next_cell) = on_grid.checked_add(increment) else { + return; + }; + if !self.lines.contains_key(&next_cell) { + self.lines.remove(&on_grid); + return; + } + on_grid = next_cell; + } + } + /// Add a line from the collection of drawn lines. + fn add(&mut self, value: f32, increment: i64) { + let mut on_grid = (value / self.width).floor() as i64; + loop { + let old_value = self.lines.insert(on_grid, increment.into()); + if old_value.is_none() { + return; + } + // TODO(clean): This fixes a panic, but I'm not sure how valid this is + let Some(added) = on_grid.checked_add(increment) else { + return; + }; + on_grid = added; + } + } +} + +pub(super) struct InsetGizmo<'w, 's> { + draw: Gizmos<'s>, + cam: CameraQuery<'w, 's>, + known_y: DrawnLines, + known_x: DrawnLines, +} +impl<'w, 's> InsetGizmo<'w, 's> { + pub(super) fn new(draw: Gizmos<'s>, cam: CameraQuery<'w, 's>, line_width: f32) -> Self { + InsetGizmo { + draw, + cam, + known_y: DrawnLines::new(line_width), + known_x: DrawnLines::new(line_width), + } + } + fn relative(&self, mut position: Vec2) -> Vec2 { + let zero = GlobalTransform::IDENTITY; + let Ok(cam) = self.cam.get_single() else { + return Vec2::ZERO; + }; + if let Some(new_position) = cam.world_to_viewport(&zero, position.extend(0.)) { + position = new_position; + }; + position.xy() + } + fn line_2d(&mut self, mut start: Vec2, mut end: Vec2, color: Color) { + if start.x.is(end.x) { + start.x = self.known_x.inset(start.x); + end.x = start.x; + } else if start.y.is(end.y) { + start.y = self.known_y.inset(start.y); + end.y = start.y; + } + let (start, end) = (self.relative(start), self.relative(end)); + self.draw.line_2d(start, end, color); + } + pub(super) fn set_scope(&mut self, rect: LayoutRect) { + let (left, right, top, bottom) = rect_border_axis(rect); + self.known_x.add(left, 1); + self.known_x.add(right, -1); + self.known_y.add(top, 1); + self.known_y.add(bottom, -1); + } + pub(super) fn clear_scope(&mut self, rect: LayoutRect) { + let (left, right, top, bottom) = rect_border_axis(rect); + self.known_x.remove(left, 1); + self.known_x.remove(right, -1); + self.known_y.remove(top, 1); + self.known_y.remove(bottom, -1); + } + pub(super) fn rect_2d(&mut self, rect: LayoutRect, color: Color) { + let (left, right, top, bottom) = rect_border_axis(rect); + if left.is(right) { + self.line_2d(Vec2::new(left, top), Vec2::new(left, bottom), color); + } else if top.is(bottom) { + self.line_2d(Vec2::new(left, top), Vec2::new(right, top), color); + } else { + let inset_x = |v| self.known_x.inset(v); + let inset_y = |v| self.known_y.inset(v); + let (left, right) = (inset_x(left), inset_x(right)); + let (top, bottom) = (inset_y(top), inset_y(bottom)); + let strip = [ + Vec2::new(left, top), + Vec2::new(left, bottom), + Vec2::new(right, bottom), + Vec2::new(right, top), + Vec2::new(left, top), + ]; + self.draw + .linestrip_2d(strip.map(|v| self.relative(v)), color); + } + } +} diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs new file mode 100644 index 0000000000000..6f4c6ee6247dc --- /dev/null +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -0,0 +1,247 @@ +//! A visual representation of UI node sizes. +use bevy_app::{App, Plugin, PostUpdate}; +use bevy_core::Name; +use bevy_core_pipeline::clear_color::ClearColorConfig; +use bevy_core_pipeline::core_2d::{Camera2d, Camera2dBundle}; +use bevy_ecs::{prelude::*, system::SystemParam}; +use bevy_gizmos::prelude::{GizmoConfig, Gizmos}; +use bevy_hierarchy::{Children, Parent}; +use bevy_input::prelude::{Input, KeyCode}; +use bevy_log::{info, warn}; +use bevy_math::{Vec2, Vec3Swizzles}; +use bevy_render::{prelude::*, view::RenderLayers}; +use bevy_transform::{prelude::GlobalTransform, TransformSystem}; +use bevy_utils::default; +use bevy_window::{PrimaryWindow, Window}; + +use crate::prelude::UiCameraConfig; +use crate::{Display, Node, Style}; +use inset::InsetGizmo; + +mod inset; + +/// The [`Camera::order`] index used by the layout debug camera. +pub const LAYOUT_DEBUG_CAMERA_ORDER: isize = 255; +/// The [`RenderLayers`] used by the debug gizmos and the debug camera. +pub const LAYOUT_DEBUG_LAYERS: RenderLayers = RenderLayers::none().with(16); + +const NODE_LIGHTNESS: f32 = 0.7; +const NODE_SATURATION: f32 = 0.8; + +fn hue_from_entity(entity: Entity) -> f32 { + const FRAC_U32MAX_GOLDEN_RATIO: u32 = 2_654_435_769; // (u32::MAX / Φ) rounded up + const RATIO_360: f32 = 360.0 / u32::MAX as f32; + entity.index().wrapping_mul(FRAC_U32MAX_GOLDEN_RATIO) as f32 * RATIO_360 +} + +#[derive(Clone, Copy)] +struct LayoutRect { + pos: Vec2, + size: Vec2, +} + +impl LayoutRect { + fn new(trans: &GlobalTransform, node: &Node) -> Self { + let mut this = Self { + pos: trans.translation().xy(), + size: node.size(), + }; + this.pos -= this.size / 2.; + this + } +} + +/// The inputs used by the `bevy_ui` debug overlay. +#[derive(Clone)] +pub struct InputMap { + /// The key used for enabling/disabling the debug overlay, default is [`KeyCode::F9`]. + pub toggle_key: KeyCode, +} +impl Default for InputMap { + fn default() -> Self { + InputMap { + toggle_key: KeyCode::F9, + } + } +} + +#[derive(Component, Debug, Clone, Default)] +struct DebugOverlayCamera; + +/// The debug overlay options. +#[derive(Resource, Clone, Default)] +pub struct Options { + /// Whether the overlay is enabled. + pub enabled: bool, + /// The inputs used by the debug overlay. + pub input_map: InputMap, + layout_gizmos_camera: Option, +} + +fn update_debug_camera( + mut gizmo_config: ResMut, + mut options: ResMut, + mut cmds: Commands, + mut debug_cams: Query<&mut Camera, With>, +) { + if !options.is_changed() && !gizmo_config.is_changed() { + return; + } + if !options.enabled { + let Some(cam) = options.layout_gizmos_camera else { + return; + }; + let Ok(mut cam) = debug_cams.get_mut(cam) else { + return; + }; + cam.is_active = false; + gizmo_config.render_layers = RenderLayers::all(); + } else { + let spawn_cam = || { + cmds.spawn(( + UiCameraConfig { show_ui: false }, + Camera2dBundle { + projection: OrthographicProjection { + far: 1000.0, + viewport_origin: Vec2::new(0.0, 0.0), + ..default() + }, + camera: Camera { + order: LAYOUT_DEBUG_CAMERA_ORDER, + ..default() + }, + camera_2d: Camera2d { + clear_color: ClearColorConfig::None, + }, + ..default() + }, + LAYOUT_DEBUG_LAYERS, + DebugOverlayCamera, + Name::new("Layout Debug Camera"), + )) + .id() + }; + gizmo_config.enabled = true; + gizmo_config.render_layers = LAYOUT_DEBUG_LAYERS; + let cam = *options.layout_gizmos_camera.get_or_insert_with(spawn_cam); + let Ok(mut cam) = debug_cams.get_mut(cam) else { + return; + }; + cam.is_active = true; + } +} + +fn toggle_overlay(input: Res>, mut options: ResMut) { + let map = &options.input_map; + if input.just_pressed(map.toggle_key) { + options.enabled = !options.enabled; + let mode = if options.enabled { + "Enabled" + } else { + "Disabled" + }; + info!("{mode} UI node preview"); + } +} + +fn outline_nodes(outline: &OutlineParam, draw: &mut InsetGizmo, this_entity: Entity) { + let Ok(to_iter) = outline.children.get(this_entity) else { + return; + }; + for (entity, trans, node, style, children) in outline.nodes.iter_many(to_iter) { + if style.is_none() || style.is_some_and(|s| matches!(s.display, Display::None)) { + continue; + } + let rect = LayoutRect::new(trans, node); + outline_node(entity, rect, draw); + if children.is_some() { + outline_nodes(outline, draw, entity); + } + draw.clear_scope(rect); + } +} + +type NodesQuery = ( + Entity, + &'static GlobalTransform, + &'static Node, + Option<&'static Style>, + Option<&'static Children>, +); + +#[derive(SystemParam)] +struct OutlineParam<'w, 's> { + gizmo_config: Res<'w, GizmoConfig>, + children: Query<'w, 's, &'static Children>, + nodes: Query<'w, 's, NodesQuery>, +} + +type CameraQuery<'w, 's> = Query<'w, 's, &'static Camera, With>; + +fn outline_roots( + outline: OutlineParam, + draw: Gizmos, + cam: CameraQuery, + roots: Query<(Entity, &GlobalTransform, &Node), Without>, + window: Query<&Window, With>, + nonprimary_windows: Query<&Window, Without>, + options: Res, +) { + if !options.enabled { + return; + } + if !nonprimary_windows.is_empty() { + warn!( + "The layout debug view only uses the primary window scale, \ + you might notice gaps between container lines" + ); + } + let scale_factor = Window::scale_factor; + let window_scale = window.get_single().map_or(1., scale_factor) as f32; + let line_width = outline.gizmo_config.line_width / window_scale; + let mut draw = InsetGizmo::new(draw, cam, line_width); + for (entity, trans, node) in &roots { + let rect = LayoutRect::new(trans, node); + outline_node(entity, rect, &mut draw); + outline_nodes(&outline, &mut draw, entity); + } +} +fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { + let hue = hue_from_entity(entity); + let color = Color::hsl(hue, NODE_SATURATION, NODE_LIGHTNESS); + + draw.rect_2d(rect, color); + draw.set_scope(rect); +} + +/// The debug overlay plugin. +/// +/// This spawns a new camera with a low order, and draws gizmo. +/// +/// Note that while the debug plugin is enabled, gizmos cannot be used by other +/// cameras. +/// +/// disabling the plugin will give you back gizmo control. +pub struct DebugUiPlugin; +impl Plugin for DebugUiPlugin { + fn build(&self, app: &mut App) { + app.init_resource::().add_systems( + PostUpdate, + ( + toggle_overlay, + update_debug_camera, + outline_roots.after(TransformSystem::TransformPropagate), + ) + .chain(), + ); + } + fn finish(&self, _app: &mut App) { + info!( + "The bevy_ui debug overlay is active!\n\ + ----------------------------------------------\n\ + \n\ + This will show the outline of UI nodes.\n\ + Press `F9` to switch between debug mods." + ); + } +} diff --git a/crates/bevy_ui/src/lib.rs b/crates/bevy_ui/src/lib.rs index e72eb5ea777d2..fc328797862f8 100644 --- a/crates/bevy_ui/src/lib.rs +++ b/crates/bevy_ui/src/lib.rs @@ -12,6 +12,8 @@ pub mod ui_material; pub mod update; pub mod widget; +#[cfg(feature = "debug")] +mod debug_overlay; use bevy_derive::{Deref, DerefMut}; use bevy_reflect::Reflect; #[cfg(feature = "bevy_text")] @@ -160,6 +162,9 @@ impl Plugin for UiPlugin { .before(Assets::::track_assets), ), ); + #[cfg(feature = "debug")] + app.add_plugins(debug_overlay::DebugUiPlugin); + #[cfg(feature = "bevy_text")] app.add_plugins(accessibility::AccessibilityPlugin); app.add_systems(PostUpdate, { From 2b944330faf0b06958faa6a25946447c0edd9859 Mon Sep 17 00:00:00 2001 From: Nicola Papale Date: Mon, 6 Nov 2023 21:29:48 +0100 Subject: [PATCH 02/45] Document cargo feature --- docs/cargo_features.md | 1 + 1 file changed, 1 insertion(+) diff --git a/docs/cargo_features.md b/docs/cargo_features.md index 1b2258fbf6b63..c776502edd895 100644 --- a/docs/cargo_features.md +++ b/docs/cargo_features.md @@ -48,6 +48,7 @@ The default feature set enables most of the expected features of a game engine, |basis-universal|Basis Universal compressed texture support| |bevy_ci_testing|Enable systems that allow for automated testing on CI| |bevy_dynamic_plugin|Plugin for dynamic loading (using [libloading](https://crates.io/crates/libloading))| +|bevy_ui_debug|Enable the bevy_ui debug overlay| |bmp|BMP image format support| |dds|DDS compressed texture support| |debug_glam_assert|Enable assertions in debug builds to check the validity of parameters passed to glam| From 7e6092cd2f5672a1a573a2b6f73ffa1677f8160e Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 12:49:20 -0300 Subject: [PATCH 03/45] [alt] Changed debug feature name --- crates/bevy_internal/Cargo.toml | 2 +- crates/bevy_ui/Cargo.toml | 2 +- crates/bevy_ui/src/lib.rs | 4 ++-- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/crates/bevy_internal/Cargo.toml b/crates/bevy_internal/Cargo.toml index 4535aa59d4d93..22186cdabffaa 100644 --- a/crates/bevy_internal/Cargo.toml +++ b/crates/bevy_internal/Cargo.toml @@ -146,7 +146,7 @@ file_watcher = ["bevy_asset?/file_watcher"] embedded_watcher = ["bevy_asset?/embedded_watcher"] # Enable the bevy_ui debug overlay -bevy_ui_debug = ["bevy_ui?/debug"] +bevy_ui_debug = ["bevy_ui?/debug_layout"] [dependencies] # bevy diff --git a/crates/bevy_ui/Cargo.toml b/crates/bevy_ui/Cargo.toml index d28519608d01e..31dc4b04322cf 100644 --- a/crates/bevy_ui/Cargo.toml +++ b/crates/bevy_ui/Cargo.toml @@ -10,7 +10,7 @@ keywords = ["bevy"] [features] default = [] -debug = ["bevy_gizmos", "bevy_core"] +debug_layout = ["bevy_gizmos", "bevy_core"] serialize = ["serde"] [dependencies] diff --git a/crates/bevy_ui/src/lib.rs b/crates/bevy_ui/src/lib.rs index 08bca09e2c3f1..993bfc9ca2371 100644 --- a/crates/bevy_ui/src/lib.rs +++ b/crates/bevy_ui/src/lib.rs @@ -10,8 +10,8 @@ pub mod ui_material; pub mod update; pub mod widget; -#[cfg(feature = "debug")] -mod debug_overlay; +#[cfg(feature = "debug_layout")] +pub mod debug_overlay; use bevy_derive::{Deref, DerefMut}; use bevy_reflect::Reflect; #[cfg(feature = "bevy_text")] From e9dd91ba3f8a48769f6f1497af5040ecf2fd662d Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 12:50:21 -0300 Subject: [PATCH 04/45] [alt] Changed DebugUiPlugin to DefaultPlugins --- crates/bevy_internal/src/default_plugins.rs | 4 ++++ crates/bevy_ui/src/lib.rs | 2 -- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/crates/bevy_internal/src/default_plugins.rs b/crates/bevy_internal/src/default_plugins.rs index d95957ab43dbf..e8ac544f85c34 100644 --- a/crates/bevy_internal/src/default_plugins.rs +++ b/crates/bevy_internal/src/default_plugins.rs @@ -99,6 +99,10 @@ impl PluginGroup for DefaultPlugins { #[cfg(feature = "bevy_ui")] { group = group.add(bevy_ui::UiPlugin); + #[cfg(feature = "bevy_ui_debug")] + { + group = group.add(bevy_ui::debug_overlay::DebugUiPlugin::default()) + } } #[cfg(feature = "bevy_pbr")] diff --git a/crates/bevy_ui/src/lib.rs b/crates/bevy_ui/src/lib.rs index 993bfc9ca2371..e283e4f09ec55 100644 --- a/crates/bevy_ui/src/lib.rs +++ b/crates/bevy_ui/src/lib.rs @@ -160,8 +160,6 @@ impl Plugin for UiPlugin { .before(Assets::::track_assets), ), ); - #[cfg(feature = "debug")] - app.add_plugins(debug_overlay::DebugUiPlugin); #[cfg(feature = "bevy_text")] app.add_plugins(accessibility::AccessibilityPlugin); From c1b88ded6f3465034c7b774adde20966038248ff Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 12:51:26 -0300 Subject: [PATCH 05/45] [fix] Fixed new changes conflicts --- crates/bevy_ui/src/debug_overlay/mod.rs | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 6f4c6ee6247dc..977ea7ad26726 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -1,14 +1,14 @@ //! A visual representation of UI node sizes. use bevy_app::{App, Plugin, PostUpdate}; use bevy_core::Name; -use bevy_core_pipeline::clear_color::ClearColorConfig; -use bevy_core_pipeline::core_2d::{Camera2d, Camera2dBundle}; +use bevy_core_pipeline::core_2d::Camera2dBundle; use bevy_ecs::{prelude::*, system::SystemParam}; use bevy_gizmos::prelude::{GizmoConfig, Gizmos}; use bevy_hierarchy::{Children, Parent}; -use bevy_input::prelude::{Input, KeyCode}; +use bevy_input::prelude::{ButtonInput, KeyCode}; use bevy_log::{info, warn}; use bevy_math::{Vec2, Vec3Swizzles}; +use bevy_render::camera::ClearColorConfig; use bevy_render::{prelude::*, view::RenderLayers}; use bevy_transform::{prelude::GlobalTransform, TransformSystem}; use bevy_utils::default; @@ -108,10 +108,8 @@ fn update_debug_camera( }, camera: Camera { order: LAYOUT_DEBUG_CAMERA_ORDER, - ..default() - }, - camera_2d: Camera2d { clear_color: ClearColorConfig::None, + ..default() }, ..default() }, @@ -131,7 +129,7 @@ fn update_debug_camera( } } -fn toggle_overlay(input: Res>, mut options: ResMut) { +fn toggle_overlay(input: Res>, mut options: ResMut) { let map = &options.input_map; if input.just_pressed(map.toggle_key) { options.enabled = !options.enabled; From 981e5191da894ae1aba4d2664a472c3b8200d7e1 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 12:53:33 -0300 Subject: [PATCH 06/45] [alt] Changed types make easier customize toggle_key --- crates/bevy_ui/src/debug_overlay/mod.rs | 50 +++++++++++++++++-------- 1 file changed, 35 insertions(+), 15 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 977ea7ad26726..08c71a6dfa821 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -70,17 +70,26 @@ struct DebugOverlayCamera; /// The debug overlay options. #[derive(Resource, Clone, Default)] -pub struct Options { +pub struct DebugOptions { /// Whether the overlay is enabled. pub enabled: bool, /// The inputs used by the debug overlay. pub input_map: InputMap, layout_gizmos_camera: Option, } - +impl DebugOptions { + fn new(key: &KeyCode) -> Self { + Self { + input_map: InputMap { + toggle_key: key.clone(), + }, + ..Default::default() + } + } +} fn update_debug_camera( mut gizmo_config: ResMut, - mut options: ResMut, + mut options: ResMut, mut cmds: Commands, mut debug_cams: Query<&mut Camera, With>, ) { @@ -183,7 +192,7 @@ fn outline_roots( roots: Query<(Entity, &GlobalTransform, &Node), Without>, window: Query<&Window, With>, nonprimary_windows: Query<&Window, Without>, - options: Res, + options: Res, ) { if !options.enabled { return; @@ -220,18 +229,28 @@ fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { /// cameras. /// /// disabling the plugin will give you back gizmo control. -pub struct DebugUiPlugin; +pub struct DebugUiPlugin { + pub toggle_key: KeyCode, +} +impl Default for DebugUiPlugin { + fn default() -> Self { + Self { + toggle_key: KeyCode::F9, + } + } +} impl Plugin for DebugUiPlugin { fn build(&self, app: &mut App) { - app.init_resource::().add_systems( - PostUpdate, - ( - toggle_overlay, - update_debug_camera, - outline_roots.after(TransformSystem::TransformPropagate), - ) - .chain(), - ); + app.insert_resource(DebugOptions::new(&self.toggle_key)) + .add_systems( + PostUpdate, + ( + toggle_overlay, + update_debug_camera, + outline_roots.after(TransformSystem::TransformPropagate), + ) + .chain(), + ); } fn finish(&self, _app: &mut App) { info!( @@ -239,7 +258,8 @@ impl Plugin for DebugUiPlugin { ----------------------------------------------\n\ \n\ This will show the outline of UI nodes.\n\ - Press `F9` to switch between debug mods." + Press {:?} to cycle between debug modes.", + self.toggle_key ); } } From 6766d90a881d9cd84a4dc7899b9e6eff8e9619f6 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 14:25:22 -0300 Subject: [PATCH 07/45] [rem] Removed unnecessary import --- crates/bevy_ui/src/debug_overlay/mod.rs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 08c71a6dfa821..9eb8aad50b2e2 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -8,8 +8,7 @@ use bevy_hierarchy::{Children, Parent}; use bevy_input::prelude::{ButtonInput, KeyCode}; use bevy_log::{info, warn}; use bevy_math::{Vec2, Vec3Swizzles}; -use bevy_render::camera::ClearColorConfig; -use bevy_render::{prelude::*, view::RenderLayers}; +use bevy_render::{prelude::*, view::RenderLayers, camera::ClearColorConfig}; use bevy_transform::{prelude::GlobalTransform, TransformSystem}; use bevy_utils::default; use bevy_window::{PrimaryWindow, Window}; From 59729e0499f2e664d99d666e85f5a815499d0fef Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 15:05:21 -0300 Subject: [PATCH 08/45] [style] Cargo fmt --- crates/bevy_ui/src/debug_overlay/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 9eb8aad50b2e2..7ad2bd4ca34ff 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -8,7 +8,7 @@ use bevy_hierarchy::{Children, Parent}; use bevy_input::prelude::{ButtonInput, KeyCode}; use bevy_log::{info, warn}; use bevy_math::{Vec2, Vec3Swizzles}; -use bevy_render::{prelude::*, view::RenderLayers, camera::ClearColorConfig}; +use bevy_render::{camera::ClearColorConfig, prelude::*, view::RenderLayers}; use bevy_transform::{prelude::GlobalTransform, TransformSystem}; use bevy_utils::default; use bevy_window::{PrimaryWindow, Window}; From 7ea6b57392fe2319a0a5aa73349aef90f661cb15 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 15:11:33 -0300 Subject: [PATCH 09/45] [fix] Clippy warnings --- crates/bevy_ui/src/debug_overlay/mod.rs | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 7ad2bd4ca34ff..9606113beab3b 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -77,11 +77,9 @@ pub struct DebugOptions { layout_gizmos_camera: Option, } impl DebugOptions { - fn new(key: &KeyCode) -> Self { + fn new(key: KeyCode) -> Self { Self { - input_map: InputMap { - toggle_key: key.clone(), - }, + input_map: InputMap { toggle_key: key }, ..Default::default() } } @@ -203,7 +201,7 @@ fn outline_roots( ); } let scale_factor = Window::scale_factor; - let window_scale = window.get_single().map_or(1., scale_factor) as f32; + let window_scale = window.get_single().map_or(1., scale_factor); let line_width = outline.gizmo_config.line_width / window_scale; let mut draw = InsetGizmo::new(draw, cam, line_width); for (entity, trans, node) in &roots { @@ -240,7 +238,7 @@ impl Default for DebugUiPlugin { } impl Plugin for DebugUiPlugin { fn build(&self, app: &mut App) { - app.insert_resource(DebugOptions::new(&self.toggle_key)) + app.insert_resource(DebugOptions::new(self.toggle_key)) .add_systems( PostUpdate, ( From 15ad9ec8d042850480c4cbb95242c9cbe1159108 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 15:16:23 -0300 Subject: [PATCH 10/45] [fix] Fixed missing semicolon --- crates/bevy_internal/src/default_plugins.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bevy_internal/src/default_plugins.rs b/crates/bevy_internal/src/default_plugins.rs index e8ac544f85c34..f1c4b640fc81b 100644 --- a/crates/bevy_internal/src/default_plugins.rs +++ b/crates/bevy_internal/src/default_plugins.rs @@ -101,7 +101,7 @@ impl PluginGroup for DefaultPlugins { group = group.add(bevy_ui::UiPlugin); #[cfg(feature = "bevy_ui_debug")] { - group = group.add(bevy_ui::debug_overlay::DebugUiPlugin::default()) + group = group.add(bevy_ui::debug_overlay::DebugUiPlugin::default()); } } From 1dd32a5e69e37e38eeb96f358cfb62b955532278 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 16:59:15 -0300 Subject: [PATCH 11/45] [alt] Removed DebugUiPlugin from DefaultPlugins --- crates/bevy_internal/src/default_plugins.rs | 4 ---- crates/bevy_ui/src/debug_overlay/mod.rs | 3 +-- crates/bevy_ui/src/lib.rs | 2 ++ 3 files changed, 3 insertions(+), 6 deletions(-) diff --git a/crates/bevy_internal/src/default_plugins.rs b/crates/bevy_internal/src/default_plugins.rs index f1c4b640fc81b..d95957ab43dbf 100644 --- a/crates/bevy_internal/src/default_plugins.rs +++ b/crates/bevy_internal/src/default_plugins.rs @@ -99,10 +99,6 @@ impl PluginGroup for DefaultPlugins { #[cfg(feature = "bevy_ui")] { group = group.add(bevy_ui::UiPlugin); - #[cfg(feature = "bevy_ui_debug")] - { - group = group.add(bevy_ui::debug_overlay::DebugUiPlugin::default()); - } } #[cfg(feature = "bevy_pbr")] diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 9606113beab3b..e90b5e5dd0e50 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -5,8 +5,7 @@ use bevy_core_pipeline::core_2d::Camera2dBundle; use bevy_ecs::{prelude::*, system::SystemParam}; use bevy_gizmos::prelude::{GizmoConfig, Gizmos}; use bevy_hierarchy::{Children, Parent}; -use bevy_input::prelude::{ButtonInput, KeyCode}; -use bevy_log::{info, warn}; +use bevy_log::warn; use bevy_math::{Vec2, Vec3Swizzles}; use bevy_render::{camera::ClearColorConfig, prelude::*, view::RenderLayers}; use bevy_transform::{prelude::GlobalTransform, TransformSystem}; diff --git a/crates/bevy_ui/src/lib.rs b/crates/bevy_ui/src/lib.rs index e283e4f09ec55..069670817b84e 100644 --- a/crates/bevy_ui/src/lib.rs +++ b/crates/bevy_ui/src/lib.rs @@ -160,6 +160,8 @@ impl Plugin for UiPlugin { .before(Assets::::track_assets), ), ); + #[cfg(feature = "debug_layout")] + app.add_plugins(debug_overlay::DebugUiPlugin); #[cfg(feature = "bevy_text")] app.add_plugins(accessibility::AccessibilityPlugin); From d822a29da6c4483dbaa3f96979226b7412035d9c Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 6 Jan 2024 16:59:57 -0300 Subject: [PATCH 12/45] [alt] Removed keybinding and changed DebugOptions name --- crates/bevy_ui/src/debug_overlay/mod.rs | 81 +++++-------------------- 1 file changed, 14 insertions(+), 67 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index e90b5e5dd0e50..8784d845f5b4d 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -49,43 +49,24 @@ impl LayoutRect { } } -/// The inputs used by the `bevy_ui` debug overlay. -#[derive(Clone)] -pub struct InputMap { - /// The key used for enabling/disabling the debug overlay, default is [`KeyCode::F9`]. - pub toggle_key: KeyCode, -} -impl Default for InputMap { - fn default() -> Self { - InputMap { - toggle_key: KeyCode::F9, - } - } -} - #[derive(Component, Debug, Clone, Default)] struct DebugOverlayCamera; /// The debug overlay options. #[derive(Resource, Clone, Default)] -pub struct DebugOptions { +pub struct UiDebugOptions { /// Whether the overlay is enabled. pub enabled: bool, - /// The inputs used by the debug overlay. - pub input_map: InputMap, layout_gizmos_camera: Option, } -impl DebugOptions { - fn new(key: KeyCode) -> Self { - Self { - input_map: InputMap { toggle_key: key }, - ..Default::default() - } +impl UiDebugOptions { + pub fn toggle(&mut self) { + self.enabled = !self.enabled; } } fn update_debug_camera( mut gizmo_config: ResMut, - mut options: ResMut, + mut options: ResMut, mut cmds: Commands, mut debug_cams: Query<&mut Camera, With>, ) { @@ -134,19 +115,6 @@ fn update_debug_camera( } } -fn toggle_overlay(input: Res>, mut options: ResMut) { - let map = &options.input_map; - if input.just_pressed(map.toggle_key) { - options.enabled = !options.enabled; - let mode = if options.enabled { - "Enabled" - } else { - "Disabled" - }; - info!("{mode} UI node preview"); - } -} - fn outline_nodes(outline: &OutlineParam, draw: &mut InsetGizmo, this_entity: Entity) { let Ok(to_iter) = outline.children.get(this_entity) else { return; @@ -188,7 +156,7 @@ fn outline_roots( roots: Query<(Entity, &GlobalTransform, &Node), Without>, window: Query<&Window, With>, nonprimary_windows: Query<&Window, Without>, - options: Res, + options: Res, ) { if !options.enabled { return; @@ -225,37 +193,16 @@ fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { /// cameras. /// /// disabling the plugin will give you back gizmo control. -pub struct DebugUiPlugin { - pub toggle_key: KeyCode, -} -impl Default for DebugUiPlugin { - fn default() -> Self { - Self { - toggle_key: KeyCode::F9, - } - } -} +pub struct DebugUiPlugin; impl Plugin for DebugUiPlugin { fn build(&self, app: &mut App) { - app.insert_resource(DebugOptions::new(self.toggle_key)) - .add_systems( - PostUpdate, - ( - toggle_overlay, - update_debug_camera, - outline_roots.after(TransformSystem::TransformPropagate), - ) - .chain(), - ); - } - fn finish(&self, _app: &mut App) { - info!( - "The bevy_ui debug overlay is active!\n\ - ----------------------------------------------\n\ - \n\ - This will show the outline of UI nodes.\n\ - Press {:?} to cycle between debug modes.", - self.toggle_key + app.init_resource::().add_systems( + PostUpdate, + ( + update_debug_camera, + outline_roots.after(TransformSystem::TransformPropagate), + ) + .chain(), ); } } From c35f8f2323331df9a48d99d0d93b169fe85f20a6 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Mon, 8 Jan 2024 22:11:49 -0300 Subject: [PATCH 13/45] [add] Added suport to Hidden visibility --- crates/bevy_ui/src/debug_overlay/mod.rs | 23 ++++++++++++++++++++--- 1 file changed, 20 insertions(+), 3 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 8784d845f5b4d..9d248ec1f147e 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -7,6 +7,7 @@ use bevy_gizmos::prelude::{GizmoConfig, Gizmos}; use bevy_hierarchy::{Children, Parent}; use bevy_log::warn; use bevy_math::{Vec2, Vec3Swizzles}; +use bevy_render::view::VisibilitySystems; use bevy_render::{camera::ClearColorConfig, prelude::*, view::RenderLayers}; use bevy_transform::{prelude::GlobalTransform, TransformSystem}; use bevy_utils::default; @@ -119,10 +120,17 @@ fn outline_nodes(outline: &OutlineParam, draw: &mut InsetGizmo, this_entity: Ent let Ok(to_iter) = outline.children.get(this_entity) else { return; }; + for (entity, trans, node, style, children) in outline.nodes.iter_many(to_iter) { if style.is_none() || style.is_some_and(|s| matches!(s.display, Display::None)) { continue; } + + if let Ok(view_visibility) = outline.view_visibility.get(entity) { + if !view_visibility.get() { + continue; + } + } let rect = LayoutRect::new(trans, node); outline_node(entity, rect, draw); if children.is_some() { @@ -145,6 +153,7 @@ struct OutlineParam<'w, 's> { gizmo_config: Res<'w, GizmoConfig>, children: Query<'w, 's, &'static Children>, nodes: Query<'w, 's, NodesQuery>, + view_visibility: Query<'w, 's, &'static ViewVisibility>, } type CameraQuery<'w, 's> = Query<'w, 's, &'static Camera, With>; @@ -153,7 +162,7 @@ fn outline_roots( outline: OutlineParam, draw: Gizmos, cam: CameraQuery, - roots: Query<(Entity, &GlobalTransform, &Node), Without>, + roots: Query<(Entity, &GlobalTransform, &Node, Option<&ViewVisibility>), Without>, window: Query<&Window, With>, nonprimary_windows: Query<&Window, Without>, options: Res, @@ -171,7 +180,13 @@ fn outline_roots( let window_scale = window.get_single().map_or(1., scale_factor); let line_width = outline.gizmo_config.line_width / window_scale; let mut draw = InsetGizmo::new(draw, cam, line_width); - for (entity, trans, node) in &roots { + for (entity, trans, node, view_visibility) in &roots { + if let Some(view_visibility) = view_visibility { + // If the entity isn't visible, we will not drawn any lines. + if !view_visibility.get() { + continue; + } + } let rect = LayoutRect::new(trans, node); outline_node(entity, rect, &mut draw); outline_nodes(&outline, &mut draw, entity); @@ -200,7 +215,9 @@ impl Plugin for DebugUiPlugin { PostUpdate, ( update_debug_camera, - outline_roots.after(TransformSystem::TransformPropagate), + outline_roots + .after(TransformSystem::TransformPropagate) + .before(VisibilitySystems::VisibilityPropagate), ) .chain(), ); From fad14d7732eeab9c93013cd355558841d8dc6cea Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Tue, 9 Jan 2024 20:54:27 -0300 Subject: [PATCH 14/45] [add] Added support to UiScale --- crates/bevy_ui/src/debug_overlay/mod.rs | 25 ++++++++++++++----------- 1 file changed, 14 insertions(+), 11 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 9d248ec1f147e..c718f8c771b42 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -14,7 +14,7 @@ use bevy_utils::default; use bevy_window::{PrimaryWindow, Window}; use crate::prelude::UiCameraConfig; -use crate::{Display, Node, Style}; +use crate::{Display, Node, Style, UiScale}; use inset::InsetGizmo; mod inset; @@ -40,10 +40,10 @@ struct LayoutRect { } impl LayoutRect { - fn new(trans: &GlobalTransform, node: &Node) -> Self { + fn new(trans: &GlobalTransform, node: &Node, scale: f32) -> Self { let mut this = Self { - pos: trans.translation().xy(), - size: node.size(), + pos: trans.translation().xy() * scale, + size: node.size() * scale, }; this.pos -= this.size / 2.; this @@ -116,7 +116,7 @@ fn update_debug_camera( } } -fn outline_nodes(outline: &OutlineParam, draw: &mut InsetGizmo, this_entity: Entity) { +fn outline_nodes(outline: &OutlineParam, draw: &mut InsetGizmo, this_entity: Entity, scale: f32) { let Ok(to_iter) = outline.children.get(this_entity) else { return; }; @@ -131,10 +131,10 @@ fn outline_nodes(outline: &OutlineParam, draw: &mut InsetGizmo, this_entity: Ent continue; } } - let rect = LayoutRect::new(trans, node); + let rect = LayoutRect::new(trans, node, scale); outline_node(entity, rect, draw); if children.is_some() { - outline_nodes(outline, draw, entity); + outline_nodes(outline, draw, entity, scale); } draw.clear_scope(rect); } @@ -166,6 +166,7 @@ fn outline_roots( window: Query<&Window, With>, nonprimary_windows: Query<&Window, Without>, options: Res, + ui_scale: Res, ) { if !options.enabled { return; @@ -176,8 +177,10 @@ fn outline_roots( you might notice gaps between container lines" ); } - let scale_factor = Window::scale_factor; - let window_scale = window.get_single().map_or(1., scale_factor); + let window_scale = window.get_single().map_or(1., Window::scale_factor); + let scale_factor = window_scale * ui_scale.0; + + // We let the line be defined by the window scale alone let line_width = outline.gizmo_config.line_width / window_scale; let mut draw = InsetGizmo::new(draw, cam, line_width); for (entity, trans, node, view_visibility) in &roots { @@ -187,9 +190,9 @@ fn outline_roots( continue; } } - let rect = LayoutRect::new(trans, node); + let rect = LayoutRect::new(trans, node, scale_factor); outline_node(entity, rect, &mut draw); - outline_nodes(&outline, &mut draw, entity); + outline_nodes(&outline, &mut draw, entity, scale_factor); } } fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { From c5bbbc6503c261c80be4993a6215f304c938d0f0 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Tue, 9 Jan 2024 21:08:00 -0300 Subject: [PATCH 15/45] [fix] Clippy warning --- crates/bevy_ui/src/debug_overlay/mod.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index c718f8c771b42..117236ec0d07f 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -154,6 +154,7 @@ struct OutlineParam<'w, 's> { children: Query<'w, 's, &'static Children>, nodes: Query<'w, 's, NodesQuery>, view_visibility: Query<'w, 's, &'static ViewVisibility>, + ui_scale: Res<'w, UiScale>, } type CameraQuery<'w, 's> = Query<'w, 's, &'static Camera, With>; @@ -166,7 +167,6 @@ fn outline_roots( window: Query<&Window, With>, nonprimary_windows: Query<&Window, Without>, options: Res, - ui_scale: Res, ) { if !options.enabled { return; @@ -178,7 +178,7 @@ fn outline_roots( ); } let window_scale = window.get_single().map_or(1., Window::scale_factor); - let scale_factor = window_scale * ui_scale.0; + let scale_factor = window_scale * outline.ui_scale.0; // We let the line be defined by the window scale alone let line_width = outline.gizmo_config.line_width / window_scale; From 5f2f9f35b38fa4f81d06180ce8df2b4fcbff3621 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Fri, 12 Jan 2024 19:44:05 -0300 Subject: [PATCH 16/45] [doc] Added extra docs --- crates/bevy_ui/src/debug_overlay/mod.rs | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 117236ec0d07f..ff34e22ea30a7 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -61,10 +61,13 @@ pub struct UiDebugOptions { layout_gizmos_camera: Option, } impl UiDebugOptions { + /// This will toggle the enabled field, setting it to false if true and true if false. pub fn toggle(&mut self) { self.enabled = !self.enabled; } } + +/// The system responsible to change the [`Camera`] config based on changes in [`UiDebugOptions`] and [`GizmoConfig`]. fn update_debug_camera( mut gizmo_config: ResMut, mut options: ResMut, @@ -116,6 +119,7 @@ fn update_debug_camera( } } +/// The function that goes over every children of given [`Entity`], skipping the not visible ones and drawing the gizmos outlines. fn outline_nodes(outline: &OutlineParam, draw: &mut InsetGizmo, this_entity: Entity, scale: f32) { let Ok(to_iter) = outline.children.get(this_entity) else { return; @@ -159,6 +163,7 @@ struct OutlineParam<'w, 's> { type CameraQuery<'w, 's> = Query<'w, 's, &'static Camera, With>; +/// system responsible for drawing the gizmos lines around all the node roots, iterating recursively through all visible children. fn outline_roots( outline: OutlineParam, draw: Gizmos, @@ -195,6 +200,8 @@ fn outline_roots( outline_nodes(&outline, &mut draw, entity, scale_factor); } } + +/// Function responsible for drawing the gizmos lines around the given Entity fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { let hue = hue_from_entity(entity); let color = Color::hsl(hue, NODE_SATURATION, NODE_LIGHTNESS); @@ -220,6 +227,7 @@ impl Plugin for DebugUiPlugin { update_debug_camera, outline_roots .after(TransformSystem::TransformPropagate) + // This needs to run before VisibilityPropagate so it can relies on ViewVisibility .before(VisibilitySystems::VisibilityPropagate), ) .chain(), From 47022f20d53e5edaa634f182fe771af3244c6b35 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 13 Jan 2024 11:06:14 -0300 Subject: [PATCH 17/45] [add] Added toggle_overlay system in ui example --- examples/ui/ui.rs | 26 +++++++++++++++++++++----- 1 file changed, 21 insertions(+), 5 deletions(-) diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index 21817b62e7f76..2332a501afd7f 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -11,13 +11,17 @@ use bevy::{ }; fn main() { - App::new() - .add_plugins(DefaultPlugins) - // Only run the app when there is user input. This will significantly reduce CPU/GPU use. + let mut app = App::new(); + app.add_plugins(DefaultPlugins) .insert_resource(WinitSettings::desktop_app()) + // Only run the app when there is user input. This will significantly reduce CPU/GPU use. .add_systems(Startup, setup) - .add_systems(Update, mouse_scroll) - .run(); + .add_systems(Update, mouse_scroll); + + #[cfg(feature = "bevy_ui_debug")] + app.add_systems(Update, toggle_overlay); + + app.run(); } fn setup(mut commands: Commands, asset_server: Res) { @@ -335,3 +339,15 @@ fn mouse_scroll( } } } + +#[cfg(feature = "bevy_ui_debug")] +// The system that will enable/disable the debug outlines around the nodes +fn toggle_overlay( + input: Res>, + mut options: ResMut, +) { + if input.just_pressed(KeyCode::Space) { + // The toggle method will enable the debug_overlay if disabled and disable if enabled + options.toggle(); + } +} From cb57e6efac285490fcea0cb4ccdcd86e45e225f9 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 13 Jan 2024 11:07:28 -0300 Subject: [PATCH 18/45] [add] Added text to warn the user about the feature --- examples/ui/ui.rs | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index 2332a501afd7f..df827ec30458e 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -57,6 +57,7 @@ fn setup(mut commands: Commands, asset_server: Res) { .spawn(NodeBundle { style: Style { width: Val::Percent(100.), + flex_direction: FlexDirection::Column, ..default() }, background_color: Color::rgb(0.15, 0.15, 0.15).into(), @@ -82,6 +83,20 @@ fn setup(mut commands: Commands, asset_server: Res) { // for accessibility to treat the text accordingly. Label, )); + + #[cfg(feature = "bevy_ui_debug")] + // Debug overlay text + parent.spawn(( + TextBundle::from_section( + "Press Space to enable debug outlines.", + TextStyle { + font: asset_server.load("fonts/FiraSans-Bold.ttf"), + font_size: 20., + ..Default::default() + }, + ), + Label, + )); }); }); // right vertical fill From 27332f736ca972dc60a6930fd32cc5d9a96ca88a Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 13 Jan 2024 11:18:45 -0300 Subject: [PATCH 19/45] [fix] Fixed comment position --- examples/ui/ui.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index df827ec30458e..74750fd07bbfe 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -13,8 +13,8 @@ use bevy::{ fn main() { let mut app = App::new(); app.add_plugins(DefaultPlugins) - .insert_resource(WinitSettings::desktop_app()) // Only run the app when there is user input. This will significantly reduce CPU/GPU use. + .insert_resource(WinitSettings::desktop_app()) .add_systems(Startup, setup) .add_systems(Update, mouse_scroll); From bfee273e99fed5eae4c779db29c4a91ff491d4c0 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 13 Jan 2024 11:19:14 -0300 Subject: [PATCH 20/45] [add] Added info to enabled feature --- examples/ui/ui.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index 74750fd07bbfe..a18767df146dd 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -361,6 +361,7 @@ fn toggle_overlay( input: Res>, mut options: ResMut, ) { + info_once!("The debug outlines are enabled, press Space to turn them on/off"); if input.just_pressed(KeyCode::Space) { // The toggle method will enable the debug_overlay if disabled and disable if enabled options.toggle(); From 408983464d6d03e6aa0fe0a3ef6e8c9bd82cb2ac Mon Sep 17 00:00:00 2001 From: pablo-lua <126117294+pablo-lua@users.noreply.github.com> Date: Sat, 13 Jan 2024 11:20:45 -0300 Subject: [PATCH 21/45] [doc] Fixed docs Co-authored-by: Alice Cecile --- crates/bevy_ui/src/debug_overlay/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index ff34e22ea30a7..17a74b133ba38 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -217,7 +217,7 @@ fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { /// Note that while the debug plugin is enabled, gizmos cannot be used by other /// cameras. /// -/// disabling the plugin will give you back gizmo control. +/// Disabling the plugin will give you back gizmo control. pub struct DebugUiPlugin; impl Plugin for DebugUiPlugin { fn build(&self, app: &mut App) { From 202fb95f6411004e311136387a6ea81eedea3320 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Mon, 15 Jan 2024 19:41:31 -0300 Subject: [PATCH 22/45] [add] Added text when user doesn't enable bevy_ui_debug --- examples/ui/ui.rs | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index a18767df146dd..4d00f72708340 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -97,6 +97,20 @@ fn setup(mut commands: Commands, asset_server: Res) { ), Label, )); + + #[cfg(not(feature = "bevy_ui_debug"))] + parent.spawn(( + TextBundle::from_section( + "Try enabling feature \"bevy_ui_debug\".", + TextStyle { + font: asset_server.load("fonts/FiraSans-Bold.ttf"), + font_size: 20., + ..Default::default() + }, + ), + Label, + )); + }); }); // right vertical fill From 15353a0caa710d01db15808545241a07b57568a4 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Mon, 15 Jan 2024 19:43:22 -0300 Subject: [PATCH 23/45] [style] Cargo fmt --- examples/ui/ui.rs | 1 - 1 file changed, 1 deletion(-) diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index 4d00f72708340..75bb357d03174 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -110,7 +110,6 @@ fn setup(mut commands: Commands, asset_server: Res) { ), Label, )); - }); }); // right vertical fill From 4e3b422ff489afaa57e1161eeaf59506dcd68ac7 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 3 Feb 2024 18:58:23 -0300 Subject: [PATCH 24/45] [fix] Fixed wrong behavior caused by update in ui --- crates/bevy_ui/src/debug_overlay/inset.rs | 10 ++- crates/bevy_ui/src/debug_overlay/mod.rs | 81 +++++++++++++++++------ 2 files changed, 69 insertions(+), 22 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/inset.rs b/crates/bevy_ui/src/debug_overlay/inset.rs index 276bcfd639f1d..ab13a3f854438 100644 --- a/crates/bevy_ui/src/debug_overlay/inset.rs +++ b/crates/bevy_ui/src/debug_overlay/inset.rs @@ -1,5 +1,6 @@ -use bevy_gizmos::prelude::Gizmos; +use bevy_gizmos::{prelude::Gizmos, config::GizmoConfigGroup}; use bevy_math::{Vec2, Vec2Swizzles}; +use bevy_reflect::Reflect; use bevy_render::prelude::Color; use bevy_transform::prelude::GlobalTransform; use bevy_utils::HashMap; @@ -114,14 +115,17 @@ impl DrawnLines { } } +#[derive(GizmoConfigGroup, Reflect, Default)] +pub struct UiGizmosDebug; + pub(super) struct InsetGizmo<'w, 's> { - draw: Gizmos<'s>, + draw: Gizmos<'w, 's, UiGizmosDebug>, cam: CameraQuery<'w, 's>, known_y: DrawnLines, known_x: DrawnLines, } impl<'w, 's> InsetGizmo<'w, 's> { - pub(super) fn new(draw: Gizmos<'s>, cam: CameraQuery<'w, 's>, line_width: f32) -> Self { + pub(super) fn new(draw: Gizmos<'w, 's, UiGizmosDebug>, cam: CameraQuery<'w, 's>, line_width: f32) -> Self { InsetGizmo { draw, cam, diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 17a74b133ba38..391a30caf2580 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -1,22 +1,27 @@ //! A visual representation of UI node sizes. +use std::any::Any; + use bevy_app::{App, Plugin, PostUpdate}; use bevy_core::Name; use bevy_core_pipeline::core_2d::Camera2dBundle; use bevy_ecs::{prelude::*, system::SystemParam}; -use bevy_gizmos::prelude::{GizmoConfig, Gizmos}; +use bevy_gizmos::AppGizmoBuilder; +use bevy_gizmos::config::GizmoConfigStore; +use bevy_gizmos::prelude::Gizmos; use bevy_hierarchy::{Children, Parent}; -use bevy_log::warn; use bevy_math::{Vec2, Vec3Swizzles}; +use bevy_render::camera::RenderTarget; use bevy_render::view::VisibilitySystems; use bevy_render::{camera::ClearColorConfig, prelude::*, view::RenderLayers}; use bevy_transform::{prelude::GlobalTransform, TransformSystem}; -use bevy_utils::default; -use bevy_window::{PrimaryWindow, Window}; +use bevy_utils::{default, warn_once}; +use bevy_window::{PrimaryWindow, Window, WindowRef}; -use crate::prelude::UiCameraConfig; -use crate::{Display, Node, Style, UiScale}; +use crate::{DefaultUiCamera, Display, Node, Style, TargetCamera, UiScale}; use inset::InsetGizmo; +use self::inset::UiGizmosDebug; + mod inset; /// The [`Camera::order`] index used by the layout debug camera. @@ -69,7 +74,7 @@ impl UiDebugOptions { /// The system responsible to change the [`Camera`] config based on changes in [`UiDebugOptions`] and [`GizmoConfig`]. fn update_debug_camera( - mut gizmo_config: ResMut, + mut gizmo_config: ResMut, mut options: ResMut, mut cmds: Commands, mut debug_cams: Query<&mut Camera, With>, @@ -85,11 +90,12 @@ fn update_debug_camera( return; }; cam.is_active = false; - gizmo_config.render_layers = RenderLayers::all(); + if let Some((config, _)) = gizmo_config.get_config_mut_dyn(&UiGizmosDebug.type_id()) { + config.render_layers = RenderLayers::all(); + } } else { let spawn_cam = || { cmds.spawn(( - UiCameraConfig { show_ui: false }, Camera2dBundle { projection: OrthographicProjection { far: 1000.0, @@ -109,8 +115,10 @@ fn update_debug_camera( )) .id() }; - gizmo_config.enabled = true; - gizmo_config.render_layers = LAYOUT_DEBUG_LAYERS; + if let Some((config, _)) = gizmo_config.get_config_mut_dyn(&UiGizmosDebug.type_id()) { + config.enabled = true; + config.render_layers = LAYOUT_DEBUG_LAYERS; + } let cam = *options.layout_gizmos_camera.get_or_insert_with(spawn_cam); let Ok(mut cam) = debug_cams.get_mut(cam) else { return; @@ -154,7 +162,7 @@ type NodesQuery = ( #[derive(SystemParam)] struct OutlineParam<'w, 's> { - gizmo_config: Res<'w, GizmoConfig>, + gizmo_config: Res<'w, GizmoConfigStore>, children: Query<'w, 's, &'static Children>, nodes: Query<'w, 's, NodesQuery>, view_visibility: Query<'w, 's, &'static ViewVisibility>, @@ -163,12 +171,20 @@ struct OutlineParam<'w, 's> { type CameraQuery<'w, 's> = Query<'w, 's, &'static Camera, With>; +#[derive(SystemParam)] +struct CameraParam<'w, 's> { + debug_camera: Query<'w, 's, &'static Camera, With>, + cameras: Query<'w, 's, &'static Camera, Without>, + primary_window: Query<'w, 's, &'static Window, With>, + default_ui_camera: DefaultUiCamera<'w, 's> +} + /// system responsible for drawing the gizmos lines around all the node roots, iterating recursively through all visible children. fn outline_roots( outline: OutlineParam, - draw: Gizmos, - cam: CameraQuery, - roots: Query<(Entity, &GlobalTransform, &Node, Option<&ViewVisibility>), Without>, + draw: Gizmos, + cam: CameraParam, + roots: Query<(Entity, &GlobalTransform, &Node, Option<&ViewVisibility>, Option<&TargetCamera>), Without>, window: Query<&Window, With>, nonprimary_windows: Query<&Window, Without>, options: Res, @@ -186,15 +202,40 @@ fn outline_roots( let scale_factor = window_scale * outline.ui_scale.0; // We let the line be defined by the window scale alone - let line_width = outline.gizmo_config.line_width / window_scale; - let mut draw = InsetGizmo::new(draw, cam, line_width); - for (entity, trans, node, view_visibility) in &roots { + let line_width = outline.gizmo_config.get_config_dyn(&UiGizmosDebug.type_id()).map_or(2., |(config, _)| config.line_width) / window_scale; + let mut draw = InsetGizmo::new(draw, cam.debug_camera, line_width); + for (entity, trans, node, view_visibility, maybe_target_camera) in &roots { if let Some(view_visibility) = view_visibility { // If the entity isn't visible, we will not drawn any lines. if !view_visibility.get() { continue; } } + // We skip ui in other windows that are not the primary one + if let Some(camera_entity) = maybe_target_camera.map(|target| {target.0}).or(cam.default_ui_camera.get()) { + let Ok(camera) = cam.cameras.get(camera_entity) else { + // The camera wasn't found. Either the Camera don't exist or the Camera is the debug Camera, that we want to skip and warn + warn_once!("Camera {:?} wasn't found for debug overlay", camera_entity); + continue; + }; + match camera.target { + RenderTarget::Window(window_ref) => { + match window_ref { + WindowRef::Entity(window_entity) => { + if cam.primary_window.get(window_entity).is_err() { + // This window isn't the primary, so we skip this root. + continue; + } + } + _ => {} + } + } + // Hard to know the results of this, better skip this target. + _ => continue + } + + } + let rect = LayoutRect::new(trans, node, scale_factor); outline_node(entity, rect, &mut draw); outline_nodes(&outline, &mut draw, entity, scale_factor); @@ -221,7 +262,9 @@ fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { pub struct DebugUiPlugin; impl Plugin for DebugUiPlugin { fn build(&self, app: &mut App) { - app.init_resource::().add_systems( + app.init_resource::() + .init_gizmo_group::() + .add_systems( PostUpdate, ( update_debug_camera, From 95cfd6e0abbea9cd8f2f053e958664cfec9da7e8 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 3 Feb 2024 18:58:44 -0300 Subject: [PATCH 25/45] [alt] Improved warn message to warn only once --- crates/bevy_ui/src/debug_overlay/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 391a30caf2580..732e4ef240090 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -193,7 +193,7 @@ fn outline_roots( return; } if !nonprimary_windows.is_empty() { - warn!( + warn_once!( "The layout debug view only uses the primary window scale, \ you might notice gaps between container lines" ); From affc06c80861101bffef58bff92a507815ce9bb7 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 3 Feb 2024 18:59:08 -0300 Subject: [PATCH 26/45] [add] Added marker component to Ui example camera --- examples/ui/ui.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index 75bb357d03174..20a25cad6a77b 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -26,7 +26,7 @@ fn main() { fn setup(mut commands: Commands, asset_server: Res) { // Camera - commands.spawn(Camera2dBundle::default()); + commands.spawn((Camera2dBundle::default(), IsDefaultUiCamera)); // root node commands From 61d90d57d58800fd5f2dd1d249e4bb87b1d45cd8 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 3 Feb 2024 19:00:09 -0300 Subject: [PATCH 27/45] [style] Cargo fmt --- crates/bevy_ui/src/debug_overlay/inset.rs | 8 +++- crates/bevy_ui/src/debug_overlay/mod.rs | 53 +++++++++++++++-------- 2 files changed, 40 insertions(+), 21 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/inset.rs b/crates/bevy_ui/src/debug_overlay/inset.rs index ab13a3f854438..1babdbaa7ac0f 100644 --- a/crates/bevy_ui/src/debug_overlay/inset.rs +++ b/crates/bevy_ui/src/debug_overlay/inset.rs @@ -1,4 +1,4 @@ -use bevy_gizmos::{prelude::Gizmos, config::GizmoConfigGroup}; +use bevy_gizmos::{config::GizmoConfigGroup, prelude::Gizmos}; use bevy_math::{Vec2, Vec2Swizzles}; use bevy_reflect::Reflect; use bevy_render::prelude::Color; @@ -125,7 +125,11 @@ pub(super) struct InsetGizmo<'w, 's> { known_x: DrawnLines, } impl<'w, 's> InsetGizmo<'w, 's> { - pub(super) fn new(draw: Gizmos<'w, 's, UiGizmosDebug>, cam: CameraQuery<'w, 's>, line_width: f32) -> Self { + pub(super) fn new( + draw: Gizmos<'w, 's, UiGizmosDebug>, + cam: CameraQuery<'w, 's>, + line_width: f32, + ) -> Self { InsetGizmo { draw, cam, diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 732e4ef240090..68d00a2561ef0 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -5,9 +5,9 @@ use bevy_app::{App, Plugin, PostUpdate}; use bevy_core::Name; use bevy_core_pipeline::core_2d::Camera2dBundle; use bevy_ecs::{prelude::*, system::SystemParam}; -use bevy_gizmos::AppGizmoBuilder; use bevy_gizmos::config::GizmoConfigStore; use bevy_gizmos::prelude::Gizmos; +use bevy_gizmos::AppGizmoBuilder; use bevy_hierarchy::{Children, Parent}; use bevy_math::{Vec2, Vec3Swizzles}; use bevy_render::camera::RenderTarget; @@ -176,7 +176,7 @@ struct CameraParam<'w, 's> { debug_camera: Query<'w, 's, &'static Camera, With>, cameras: Query<'w, 's, &'static Camera, Without>, primary_window: Query<'w, 's, &'static Window, With>, - default_ui_camera: DefaultUiCamera<'w, 's> + default_ui_camera: DefaultUiCamera<'w, 's>, } /// system responsible for drawing the gizmos lines around all the node roots, iterating recursively through all visible children. @@ -184,7 +184,16 @@ fn outline_roots( outline: OutlineParam, draw: Gizmos, cam: CameraParam, - roots: Query<(Entity, &GlobalTransform, &Node, Option<&ViewVisibility>, Option<&TargetCamera>), Without>, + roots: Query< + ( + Entity, + &GlobalTransform, + &Node, + Option<&ViewVisibility>, + Option<&TargetCamera>, + ), + Without, + >, window: Query<&Window, With>, nonprimary_windows: Query<&Window, Without>, options: Res, @@ -202,7 +211,11 @@ fn outline_roots( let scale_factor = window_scale * outline.ui_scale.0; // We let the line be defined by the window scale alone - let line_width = outline.gizmo_config.get_config_dyn(&UiGizmosDebug.type_id()).map_or(2., |(config, _)| config.line_width) / window_scale; + let line_width = outline + .gizmo_config + .get_config_dyn(&UiGizmosDebug.type_id()) + .map_or(2., |(config, _)| config.line_width) + / window_scale; let mut draw = InsetGizmo::new(draw, cam.debug_camera, line_width); for (entity, trans, node, view_visibility, maybe_target_camera) in &roots { if let Some(view_visibility) = view_visibility { @@ -212,7 +225,10 @@ fn outline_roots( } } // We skip ui in other windows that are not the primary one - if let Some(camera_entity) = maybe_target_camera.map(|target| {target.0}).or(cam.default_ui_camera.get()) { + if let Some(camera_entity) = maybe_target_camera + .map(|target| target.0) + .or(cam.default_ui_camera.get()) + { let Ok(camera) = cam.cameras.get(camera_entity) else { // The camera wasn't found. Either the Camera don't exist or the Camera is the debug Camera, that we want to skip and warn warn_once!("Camera {:?} wasn't found for debug overlay", camera_entity); @@ -231,9 +247,8 @@ fn outline_roots( } } // Hard to know the results of this, better skip this target. - _ => continue + _ => continue, } - } let rect = LayoutRect::new(trans, node, scale_factor); @@ -263,17 +278,17 @@ pub struct DebugUiPlugin; impl Plugin for DebugUiPlugin { fn build(&self, app: &mut App) { app.init_resource::() - .init_gizmo_group::() - .add_systems( - PostUpdate, - ( - update_debug_camera, - outline_roots - .after(TransformSystem::TransformPropagate) - // This needs to run before VisibilityPropagate so it can relies on ViewVisibility - .before(VisibilitySystems::VisibilityPropagate), - ) - .chain(), - ); + .init_gizmo_group::() + .add_systems( + PostUpdate, + ( + update_debug_camera, + outline_roots + .after(TransformSystem::TransformPropagate) + // This needs to run before VisibilityPropagate so it can relies on ViewVisibility + .before(VisibilitySystems::VisibilityPropagate), + ) + .chain(), + ); } } From 8455720cd0f3e284eca6d78c89c9687fd7d6d0af Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 3 Feb 2024 19:06:11 -0300 Subject: [PATCH 28/45] [style] Improved Code quality --- crates/bevy_ui/src/debug_overlay/mod.rs | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 68d00a2561ef0..5d97fd39e7a4f 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -236,14 +236,11 @@ fn outline_roots( }; match camera.target { RenderTarget::Window(window_ref) => { - match window_ref { - WindowRef::Entity(window_entity) => { - if cam.primary_window.get(window_entity).is_err() { - // This window isn't the primary, so we skip this root. - continue; - } + if let WindowRef::Entity(window_entity) = window_ref { + if cam.primary_window.get(window_entity).is_err() { + // This window isn't the primary, so we skip this root. + continue; } - _ => {} } } // Hard to know the results of this, better skip this target. From 60ed352fa7b6d21c4690ef0da9b4d247744dc0dd Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 3 Feb 2024 19:10:48 -0300 Subject: [PATCH 29/45] [docs] Fix docs --- crates/bevy_ui/src/debug_overlay/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 5d97fd39e7a4f..fb84d9f7d410b 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -72,7 +72,7 @@ impl UiDebugOptions { } } -/// The system responsible to change the [`Camera`] config based on changes in [`UiDebugOptions`] and [`GizmoConfig`]. +/// The system responsible to change the [`Camera`] config based on changes in [`UiDebugOptions`] and [`GizmoConfig`](bevy_gizmos::prelude::GizmoConfig). fn update_debug_camera( mut gizmo_config: ResMut, mut options: ResMut, From 9c52af993edca9190c6ce0d2895ea2d14db24934 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sun, 4 Feb 2024 21:25:38 -0300 Subject: [PATCH 30/45] [fix] Little fix on comment --- crates/bevy_ui/src/debug_overlay/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index fb84d9f7d410b..31ab6af6624a1 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -219,7 +219,7 @@ fn outline_roots( let mut draw = InsetGizmo::new(draw, cam.debug_camera, line_width); for (entity, trans, node, view_visibility, maybe_target_camera) in &roots { if let Some(view_visibility) = view_visibility { - // If the entity isn't visible, we will not drawn any lines. + // If the entity isn't visible, we will not draw any lines. if !view_visibility.get() { continue; } From 12f4e64de26c43ab38a25491a6cc40fffd966303 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sun, 4 Feb 2024 21:26:46 -0300 Subject: [PATCH 31/45] [doc] Changed docs note --- crates/bevy_ui/src/debug_overlay/mod.rs | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 31ab6af6624a1..8f76456648fde 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -267,10 +267,8 @@ fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { /// /// This spawns a new camera with a low order, and draws gizmo. /// -/// Note that while the debug plugin is enabled, gizmos cannot be used by other -/// cameras. -/// -/// Disabling the plugin will give you back gizmo control. +/// Note that due to limitation with bevy_gizmos, multiple windows with this feature +/// enabled isn't supported and the lines are only drawn in the [`PrimaryWindow`] pub struct DebugUiPlugin; impl Plugin for DebugUiPlugin { fn build(&self, app: &mut App) { From d20a5d82c25bbfef7eef0e76d4213a85024f1914 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sun, 4 Feb 2024 21:50:16 -0300 Subject: [PATCH 32/45] [alt] Improvements on options settings --- crates/bevy_ui/src/debug_overlay/mod.rs | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 8f76456648fde..69207b23050aa 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -1,5 +1,5 @@ //! A visual representation of UI node sizes. -use std::any::Any; +use std::any::{Any, TypeId}; use bevy_app::{App, Plugin, PostUpdate}; use bevy_core::Name; @@ -90,8 +90,8 @@ fn update_debug_camera( return; }; cam.is_active = false; - if let Some((config, _)) = gizmo_config.get_config_mut_dyn(&UiGizmosDebug.type_id()) { - config.render_layers = RenderLayers::all(); + if let Some((config, _)) = gizmo_config.get_config_mut_dyn(&TypeId::of::()) { + config.enabled = false; } } else { let spawn_cam = || { @@ -115,7 +115,7 @@ fn update_debug_camera( )) .id() }; - if let Some((config, _)) = gizmo_config.get_config_mut_dyn(&UiGizmosDebug.type_id()) { + if let Some((config, _)) = gizmo_config.get_config_mut_dyn(&TypeId::of::()) { config.enabled = true; config.render_layers = LAYOUT_DEBUG_LAYERS; } From 494c4ddc7c6b0e2f7b4ae65a862cc68d1c6c8631 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sun, 4 Feb 2024 22:26:26 -0300 Subject: [PATCH 33/45] [doc] Fixed docs mention to extern crate --- crates/bevy_ui/src/debug_overlay/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 69207b23050aa..5128bcb7886f8 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -267,7 +267,7 @@ fn outline_node(entity: Entity, rect: LayoutRect, draw: &mut InsetGizmo) { /// /// This spawns a new camera with a low order, and draws gizmo. /// -/// Note that due to limitation with bevy_gizmos, multiple windows with this feature +/// Note that due to limitation with [`bevy_gizmos`], multiple windows with this feature /// enabled isn't supported and the lines are only drawn in the [`PrimaryWindow`] pub struct DebugUiPlugin; impl Plugin for DebugUiPlugin { From 4fd89f248bf774f3719b36327e3e827be8e1fe1e Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Thu, 22 Feb 2024 21:34:12 -0300 Subject: [PATCH 34/45] [cargo] Fix version requirement --- crates/bevy_ui/Cargo.toml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/crates/bevy_ui/Cargo.toml b/crates/bevy_ui/Cargo.toml index 94feca58d16a3..fb0f6296e3f82 100644 --- a/crates/bevy_ui/Cargo.toml +++ b/crates/bevy_ui/Cargo.toml @@ -18,11 +18,11 @@ serialize = ["serde"] bevy_a11y = { path = "../bevy_a11y", version = "0.14.0-dev" } bevy_app = { path = "../bevy_app", version = "0.14.0-dev" } bevy_asset = { path = "../bevy_asset", version = "0.14.0-dev" } -bevy_core = { path = "../bevy_core", version = "0.12.0", optional = true } +bevy_core = { path = "../bevy_core", version = "0.14.0-dev", optional = true } bevy_core_pipeline = { path = "../bevy_core_pipeline", version = "0.14.0-dev" } bevy_derive = { path = "../bevy_derive", version = "0.14.0-dev" } bevy_ecs = { path = "../bevy_ecs", version = "0.14.0-dev" } -bevy_gizmos = { path = "../bevy_gizmos", version = "0.12.0", optional = true } +bevy_gizmos = { path = "../bevy_gizmos", version = "0.14.0-dev", optional = true } bevy_hierarchy = { path = "../bevy_hierarchy", version = "0.14.0-dev" } bevy_input = { path = "../bevy_input", version = "0.14.0-dev" } bevy_log = { path = "../bevy_log", version = "0.14.0-dev" } From 56509e6661dd49472569d70d40297595254684c7 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Fri, 1 Mar 2024 20:21:12 -0300 Subject: [PATCH 35/45] [style] Cargo fmt --- crates/bevy_ui/src/debug_overlay/inset.rs | 2 +- crates/bevy_ui/src/debug_overlay/mod.rs | 6 +++++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/crates/bevy_ui/src/debug_overlay/inset.rs b/crates/bevy_ui/src/debug_overlay/inset.rs index d404522bfd723..8cb8841f13916 100644 --- a/crates/bevy_ui/src/debug_overlay/inset.rs +++ b/crates/bevy_ui/src/debug_overlay/inset.rs @@ -1,7 +1,7 @@ +use bevy_color::Color; use bevy_gizmos::{config::GizmoConfigGroup, prelude::Gizmos}; use bevy_math::{Vec2, Vec2Swizzles}; use bevy_reflect::Reflect; -use bevy_color::Color; use bevy_transform::prelude::GlobalTransform; use bevy_utils::HashMap; diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_ui/src/debug_overlay/mod.rs index 090109014c29f..83373d7408df5 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_ui/src/debug_overlay/mod.rs @@ -11,7 +11,11 @@ use bevy_gizmos::prelude::Gizmos; use bevy_gizmos::AppGizmoBuilder; use bevy_hierarchy::{Children, Parent}; use bevy_math::{Vec2, Vec3Swizzles}; -use bevy_render::{camera::{RenderTarget, ClearColorConfig}, view::{RenderLayers, VisibilitySystems}, prelude::*}; +use bevy_render::{ + camera::{ClearColorConfig, RenderTarget}, + prelude::*, + view::{RenderLayers, VisibilitySystems}, +}; use bevy_transform::{prelude::GlobalTransform, TransformSystem}; use bevy_utils::{default, warn_once}; use bevy_window::{PrimaryWindow, Window, WindowRef}; From a50f02a796efbbd1a08be1ddfcf2e013e20486b2 Mon Sep 17 00:00:00 2001 From: Pablo Reinhardt <126117294+pablo-lua@users.noreply.github.com> Date: Tue, 5 Mar 2024 14:50:16 -0300 Subject: [PATCH 36/45] Update docs.yml --- .github/workflows/docs.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml index ee3c6d848c5af..322ad9231e465 100644 --- a/.github/workflows/docs.yml +++ b/.github/workflows/docs.yml @@ -3,7 +3,7 @@ name: Deploy Docs on: push: branches: - - 'main' + - 'test' # Allows running the action manually. workflow_dispatch: From 7419481248b22b5aa90cb3986ac6b21b42ad456a Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 9 Mar 2024 12:39:55 -0300 Subject: [PATCH 37/45] [alt] Move debug_overlay to bevy_dev_tools crate --- crates/bevy_dev_tools/Cargo.toml | 12 +++++++++++- .../src/debug_overlay/inset.rs | 0 .../src/debug_overlay/mod.rs | 10 ++++++---- crates/bevy_dev_tools/src/lib.rs | 7 +++++++ crates/bevy_internal/Cargo.toml | 2 +- crates/bevy_ui/Cargo.toml | 1 - crates/bevy_ui/src/lib.rs | 4 ---- examples/ui/ui.rs | 2 +- 8 files changed, 26 insertions(+), 12 deletions(-) rename crates/{bevy_ui => bevy_dev_tools}/src/debug_overlay/inset.rs (100%) rename crates/{bevy_ui => bevy_dev_tools}/src/debug_overlay/mod.rs (98%) diff --git a/crates/bevy_dev_tools/Cargo.toml b/crates/bevy_dev_tools/Cargo.toml index 18f66b4e5a3aa..286e71f1f1aa8 100644 --- a/crates/bevy_dev_tools/Cargo.toml +++ b/crates/bevy_dev_tools/Cargo.toml @@ -10,14 +10,24 @@ keywords = ["bevy"] [features] bevy_ci_testing = ["serde", "ron"] +bevy_ui_debug = [] [dependencies] # bevy bevy_app = { path = "../bevy_app", version = "0.14.0-dev" } -bevy_utils = { path = "../bevy_utils", version = "0.14.0-dev" } +bevy_color = { path = "../bevy_color", version = "0.14.0-dev" } +bevy_core = { path = "../bevy_core", version = "0.14.0-dev" } +bevy_core_pipeline = { path = "../bevy_core_pipeline", version = "0.14.0-dev" } bevy_ecs = { path = "../bevy_ecs", version = "0.14.0-dev" } +bevy_gizmos = { path = "../bevy_gizmos", version = "0.14.0-dev" } +bevy_hierarchy = { path = "../bevy_hierarchy", version = "0.14.0-dev" } +bevy_math = { path = "../bevy_math", version = "0.14.0-dev" } +bevy_reflect = { path = "../bevy_reflect", version = "0.14.0-dev" } bevy_render = { path = "../bevy_render", version = "0.14.0-dev" } bevy_time = { path = "../bevy_time", version = "0.14.0-dev" } +bevy_transform = { path = "../bevy_transform", version = "0.14.0-dev" } +bevy_ui = { path = "../bevy_ui", version = "0.14.0-dev" } +bevy_utils = { path = "../bevy_utils", version = "0.14.0-dev" } bevy_window = { path = "../bevy_window", version = "0.14.0-dev" } # other diff --git a/crates/bevy_ui/src/debug_overlay/inset.rs b/crates/bevy_dev_tools/src/debug_overlay/inset.rs similarity index 100% rename from crates/bevy_ui/src/debug_overlay/inset.rs rename to crates/bevy_dev_tools/src/debug_overlay/inset.rs diff --git a/crates/bevy_ui/src/debug_overlay/mod.rs b/crates/bevy_dev_tools/src/debug_overlay/mod.rs similarity index 98% rename from crates/bevy_ui/src/debug_overlay/mod.rs rename to crates/bevy_dev_tools/src/debug_overlay/mod.rs index 83373d7408df5..36abee584dc7b 100644 --- a/crates/bevy_ui/src/debug_overlay/mod.rs +++ b/crates/bevy_dev_tools/src/debug_overlay/mod.rs @@ -6,9 +6,11 @@ use bevy_color::Hsla; use bevy_core::Name; use bevy_core_pipeline::core_2d::Camera2dBundle; use bevy_ecs::{prelude::*, system::SystemParam}; -use bevy_gizmos::config::GizmoConfigStore; -use bevy_gizmos::prelude::Gizmos; -use bevy_gizmos::AppGizmoBuilder; +use bevy_gizmos::{ + config::GizmoConfigStore, + prelude::Gizmos, + AppGizmoBuilder +}; use bevy_hierarchy::{Children, Parent}; use bevy_math::{Vec2, Vec3Swizzles}; use bevy_render::{ @@ -17,10 +19,10 @@ use bevy_render::{ view::{RenderLayers, VisibilitySystems}, }; use bevy_transform::{prelude::GlobalTransform, TransformSystem}; +use bevy_ui::{DefaultUiCamera, Display, Node, Style, TargetCamera, UiScale}; use bevy_utils::{default, warn_once}; use bevy_window::{PrimaryWindow, Window, WindowRef}; -use crate::{DefaultUiCamera, Display, Node, Style, TargetCamera, UiScale}; use inset::InsetGizmo; use self::inset::UiGizmosDebug; diff --git a/crates/bevy_dev_tools/src/lib.rs b/crates/bevy_dev_tools/src/lib.rs index b025539ebbb57..de05e39af7511 100644 --- a/crates/bevy_dev_tools/src/lib.rs +++ b/crates/bevy_dev_tools/src/lib.rs @@ -5,6 +5,9 @@ use bevy_app::prelude::*; #[cfg(feature = "bevy_ci_testing")] pub mod ci_testing; +#[cfg(feature = "bevy_ui_debug")] +pub mod debug_overlay; + /// Enables developer tools in an [`App`]. This plugin is added automatically with `bevy_dev_tools` /// feature. /// @@ -40,5 +43,9 @@ impl Plugin for DevToolsPlugin { { ci_testing::setup_app(_app); } + + #[cfg(feature = "bevy_ui_debug")] + _app.add_plugins(debug_overlay::DebugUiPlugin); + } } diff --git a/crates/bevy_internal/Cargo.toml b/crates/bevy_internal/Cargo.toml index 5b4421f7235ba..3f0a4e1e3abb1 100644 --- a/crates/bevy_internal/Cargo.toml +++ b/crates/bevy_internal/Cargo.toml @@ -153,7 +153,7 @@ file_watcher = ["bevy_asset?/file_watcher"] embedded_watcher = ["bevy_asset?/embedded_watcher"] # Enable the bevy_ui debug overlay -bevy_ui_debug = ["bevy_ui?/debug_layout"] +bevy_ui_debug = ["bevy_dev_tools?/bevy_ui_debug", "bevy_dev_tools"] # Enable system stepping support bevy_debug_stepping = [ diff --git a/crates/bevy_ui/Cargo.toml b/crates/bevy_ui/Cargo.toml index 5d45064ac7413..8815060c125ec 100644 --- a/crates/bevy_ui/Cargo.toml +++ b/crates/bevy_ui/Cargo.toml @@ -10,7 +10,6 @@ keywords = ["bevy"] [features] default = [] -debug_layout = ["bevy_gizmos", "bevy_core"] serialize = ["serde", "smallvec/serde"] [dependencies] diff --git a/crates/bevy_ui/src/lib.rs b/crates/bevy_ui/src/lib.rs index 0cd22738df0d0..17daf47fb1c74 100644 --- a/crates/bevy_ui/src/lib.rs +++ b/crates/bevy_ui/src/lib.rs @@ -12,8 +12,6 @@ pub mod ui_material; pub mod update; pub mod widget; -#[cfg(feature = "debug_layout")] -pub mod debug_overlay; use bevy_derive::{Deref, DerefMut}; use bevy_reflect::Reflect; #[cfg(feature = "bevy_text")] @@ -163,8 +161,6 @@ impl Plugin for UiPlugin { .chain(), ), ); - #[cfg(feature = "debug_layout")] - app.add_plugins(debug_overlay::DebugUiPlugin); #[cfg(feature = "bevy_text")] build_text_interop(app); diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index b7f573e25585c..62ad41b063875 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -371,7 +371,7 @@ fn mouse_scroll( // The system that will enable/disable the debug outlines around the nodes fn toggle_overlay( input: Res>, - mut options: ResMut, + mut options: ResMut, ) { info_once!("The debug outlines are enabled, press Space to turn them on/off"); if input.just_pressed(KeyCode::Space) { From 3f978ad88aa5639026979d21cb271bc4054b001a Mon Sep 17 00:00:00 2001 From: Pablo Reinhardt <126117294+pablo-lua@users.noreply.github.com> Date: Sat, 9 Mar 2024 12:43:33 -0300 Subject: [PATCH 38/45] [alt] Revert local change added by mistake --- .github/workflows/docs.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml index 322ad9231e465..ee3c6d848c5af 100644 --- a/.github/workflows/docs.yml +++ b/.github/workflows/docs.yml @@ -3,7 +3,7 @@ name: Deploy Docs on: push: branches: - - 'test' + - 'main' # Allows running the action manually. workflow_dispatch: From 51ef533fdc22021b916e9b3432ddd76768972e39 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 9 Mar 2024 12:54:33 -0300 Subject: [PATCH 39/45] [alt] Revert changes on ui toml --- crates/bevy_ui/Cargo.toml | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/crates/bevy_ui/Cargo.toml b/crates/bevy_ui/Cargo.toml index 8815060c125ec..a83a5069ae0b0 100644 --- a/crates/bevy_ui/Cargo.toml +++ b/crates/bevy_ui/Cargo.toml @@ -8,21 +8,15 @@ repository = "https://github.com/bevyengine/bevy" license = "MIT OR Apache-2.0" keywords = ["bevy"] -[features] -default = [] -serialize = ["serde", "smallvec/serde"] - [dependencies] # bevy bevy_a11y = { path = "../bevy_a11y", version = "0.14.0-dev" } bevy_app = { path = "../bevy_app", version = "0.14.0-dev" } bevy_asset = { path = "../bevy_asset", version = "0.14.0-dev" } bevy_color = { path = "../bevy_color", version = "0.14.0-dev" } -bevy_core = { path = "../bevy_core", version = "0.14.0-dev", optional = true } bevy_core_pipeline = { path = "../bevy_core_pipeline", version = "0.14.0-dev" } bevy_derive = { path = "../bevy_derive", version = "0.14.0-dev" } bevy_ecs = { path = "../bevy_ecs", version = "0.14.0-dev" } -bevy_gizmos = { path = "../bevy_gizmos", version = "0.14.0-dev", optional = true } bevy_hierarchy = { path = "../bevy_hierarchy", version = "0.14.0-dev" } bevy_input = { path = "../bevy_input", version = "0.14.0-dev" } bevy_math = { path = "../bevy_math", version = "0.14.0-dev" } @@ -44,5 +38,9 @@ thiserror = "1.0.0" nonmax = "0.5" smallvec = "1.11" +[features] +default = [] +serialize = ["serde", "smallvec/serde"] + [lints] workspace = true From bd26750cdbda7978cd0a42b25a9e2d4004649d5f Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 9 Mar 2024 12:54:33 -0300 Subject: [PATCH 40/45] [alt] Revert changes on ui toml --- crates/bevy_ui/Cargo.toml | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/crates/bevy_ui/Cargo.toml b/crates/bevy_ui/Cargo.toml index 8815060c125ec..b83a227e99d8d 100644 --- a/crates/bevy_ui/Cargo.toml +++ b/crates/bevy_ui/Cargo.toml @@ -8,21 +8,15 @@ repository = "https://github.com/bevyengine/bevy" license = "MIT OR Apache-2.0" keywords = ["bevy"] -[features] -default = [] -serialize = ["serde", "smallvec/serde"] - [dependencies] # bevy bevy_a11y = { path = "../bevy_a11y", version = "0.14.0-dev" } bevy_app = { path = "../bevy_app", version = "0.14.0-dev" } bevy_asset = { path = "../bevy_asset", version = "0.14.0-dev" } bevy_color = { path = "../bevy_color", version = "0.14.0-dev" } -bevy_core = { path = "../bevy_core", version = "0.14.0-dev", optional = true } bevy_core_pipeline = { path = "../bevy_core_pipeline", version = "0.14.0-dev" } bevy_derive = { path = "../bevy_derive", version = "0.14.0-dev" } bevy_ecs = { path = "../bevy_ecs", version = "0.14.0-dev" } -bevy_gizmos = { path = "../bevy_gizmos", version = "0.14.0-dev", optional = true } bevy_hierarchy = { path = "../bevy_hierarchy", version = "0.14.0-dev" } bevy_input = { path = "../bevy_input", version = "0.14.0-dev" } bevy_math = { path = "../bevy_math", version = "0.14.0-dev" } @@ -44,5 +38,8 @@ thiserror = "1.0.0" nonmax = "0.5" smallvec = "1.11" +[features] +serialize = ["serde", "smallvec/serde"] + [lints] workspace = true From 6477000c4a5292a4ef9cd9fde9b74bff25e45daf Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sat, 9 Mar 2024 13:01:15 -0300 Subject: [PATCH 41/45] [style] Cargo fmt --- crates/bevy_dev_tools/src/debug_overlay/mod.rs | 6 +----- crates/bevy_dev_tools/src/lib.rs | 1 - 2 files changed, 1 insertion(+), 6 deletions(-) diff --git a/crates/bevy_dev_tools/src/debug_overlay/mod.rs b/crates/bevy_dev_tools/src/debug_overlay/mod.rs index 36abee584dc7b..f6533c6955841 100644 --- a/crates/bevy_dev_tools/src/debug_overlay/mod.rs +++ b/crates/bevy_dev_tools/src/debug_overlay/mod.rs @@ -6,11 +6,7 @@ use bevy_color::Hsla; use bevy_core::Name; use bevy_core_pipeline::core_2d::Camera2dBundle; use bevy_ecs::{prelude::*, system::SystemParam}; -use bevy_gizmos::{ - config::GizmoConfigStore, - prelude::Gizmos, - AppGizmoBuilder -}; +use bevy_gizmos::{config::GizmoConfigStore, prelude::Gizmos, AppGizmoBuilder}; use bevy_hierarchy::{Children, Parent}; use bevy_math::{Vec2, Vec3Swizzles}; use bevy_render::{ diff --git a/crates/bevy_dev_tools/src/lib.rs b/crates/bevy_dev_tools/src/lib.rs index de05e39af7511..bc1396a55fe94 100644 --- a/crates/bevy_dev_tools/src/lib.rs +++ b/crates/bevy_dev_tools/src/lib.rs @@ -46,6 +46,5 @@ impl Plugin for DevToolsPlugin { #[cfg(feature = "bevy_ui_debug")] _app.add_plugins(debug_overlay::DebugUiPlugin); - } } From d1787a5d5c0999b223177a63d9806ae9105a2974 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sun, 10 Mar 2024 19:06:46 -0300 Subject: [PATCH 42/45] [rem] Removed bevy_ui_debug from top level features --- Cargo.toml | 3 --- crates/bevy_dev_tools/Cargo.toml | 1 + crates/bevy_dev_tools/src/lib.rs | 3 --- crates/bevy_internal/Cargo.toml | 3 --- examples/ui/ui.rs | 15 +++++++++------ 5 files changed, 10 insertions(+), 15 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index b69bed4878fac..fd5343af55a8f 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -149,9 +149,6 @@ bevy_ui = [ "bevy_color", ] -# Enable the bevy_ui debug overlay -bevy_ui_debug = ["bevy_internal/bevy_ui_debug"] - # winit window and input backend bevy_winit = ["bevy_internal/bevy_winit"] diff --git a/crates/bevy_dev_tools/Cargo.toml b/crates/bevy_dev_tools/Cargo.toml index 8b8a0fcace487..6babe134627cf 100644 --- a/crates/bevy_dev_tools/Cargo.toml +++ b/crates/bevy_dev_tools/Cargo.toml @@ -9,6 +9,7 @@ license = "MIT OR Apache-2.0" keywords = ["bevy"] [features] +default = ["bevy_ui_debug"] bevy_ci_testing = ["serde", "ron"] bevy_ui_debug = [] diff --git a/crates/bevy_dev_tools/src/lib.rs b/crates/bevy_dev_tools/src/lib.rs index d50583a50935b..62a52cf5778ca 100644 --- a/crates/bevy_dev_tools/src/lib.rs +++ b/crates/bevy_dev_tools/src/lib.rs @@ -44,8 +44,5 @@ impl Plugin for DevToolsPlugin { { ci_testing::setup_app(_app); } - - #[cfg(feature = "bevy_ui_debug")] - _app.add_plugins(debug_overlay::DebugUiPlugin); } } diff --git a/crates/bevy_internal/Cargo.toml b/crates/bevy_internal/Cargo.toml index 3f0a4e1e3abb1..68cb7421d3106 100644 --- a/crates/bevy_internal/Cargo.toml +++ b/crates/bevy_internal/Cargo.toml @@ -152,9 +152,6 @@ file_watcher = ["bevy_asset?/file_watcher"] # Enables watching embedded files for Bevy Asset hot-reloading embedded_watcher = ["bevy_asset?/embedded_watcher"] -# Enable the bevy_ui debug overlay -bevy_ui_debug = ["bevy_dev_tools?/bevy_ui_debug", "bevy_dev_tools"] - # Enable system stepping support bevy_debug_stepping = [ "bevy_ecs/bevy_debug_stepping", diff --git a/examples/ui/ui.rs b/examples/ui/ui.rs index 62ad41b063875..585d69ee389d0 100644 --- a/examples/ui/ui.rs +++ b/examples/ui/ui.rs @@ -19,8 +19,11 @@ fn main() { .add_systems(Startup, setup) .add_systems(Update, mouse_scroll); - #[cfg(feature = "bevy_ui_debug")] - app.add_systems(Update, toggle_overlay); + #[cfg(feature = "bevy_dev_tools")] + { + app.add_plugins(bevy::dev_tools::debug_overlay::DebugUiPlugin) + .add_systems(Update, toggle_overlay); + } app.run(); } @@ -85,7 +88,7 @@ fn setup(mut commands: Commands, asset_server: Res) { Label, )); - #[cfg(feature = "bevy_ui_debug")] + #[cfg(feature = "bevy_dev_tools")] // Debug overlay text parent.spawn(( TextBundle::from_section( @@ -99,10 +102,10 @@ fn setup(mut commands: Commands, asset_server: Res) { Label, )); - #[cfg(not(feature = "bevy_ui_debug"))] + #[cfg(not(feature = "bevy_dev_tools"))] parent.spawn(( TextBundle::from_section( - "Try enabling feature \"bevy_ui_debug\".", + "Try enabling feature \"bevy_dev_tools\".", TextStyle { font: asset_server.load("fonts/FiraSans-Bold.ttf"), font_size: 20., @@ -367,7 +370,7 @@ fn mouse_scroll( } } -#[cfg(feature = "bevy_ui_debug")] +#[cfg(feature = "bevy_dev_tools")] // The system that will enable/disable the debug outlines around the nodes fn toggle_overlay( input: Res>, From 434cd2e38303de54f8d0ca4dfc58d24f58466f03 Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sun, 10 Mar 2024 19:08:55 -0300 Subject: [PATCH 43/45] [rem] Removed trait ApproxF32 --- .../bevy_dev_tools/src/debug_overlay/inset.rs | 19 +++++++------------ 1 file changed, 7 insertions(+), 12 deletions(-) diff --git a/crates/bevy_dev_tools/src/debug_overlay/inset.rs b/crates/bevy_dev_tools/src/debug_overlay/inset.rs index 8cb8841f13916..86be2146c73d7 100644 --- a/crates/bevy_dev_tools/src/debug_overlay/inset.rs +++ b/crates/bevy_dev_tools/src/debug_overlay/inset.rs @@ -7,14 +7,9 @@ use bevy_utils::HashMap; use super::{CameraQuery, LayoutRect}; -trait ApproxF32 { - fn is(self, other: f32) -> bool; -} -impl ApproxF32 for f32 { - fn is(self, other: f32) -> bool { - let diff = (self - other).abs(); - diff < 0.001 - } +// Function used here so we don't need to redraw lines that are fairly close to each other. +fn approx_eq(compared: f32, other: f32) -> bool { + (compared - other).abs() < 0.001 } fn rect_border_axis(rect: LayoutRect) -> (f32, f32, f32, f32) { @@ -148,10 +143,10 @@ impl<'w, 's> InsetGizmo<'w, 's> { position.xy() } fn line_2d(&mut self, mut start: Vec2, mut end: Vec2, color: Color) { - if start.x.is(end.x) { + if approx_eq(start.x, end.x) { start.x = self.known_x.inset(start.x); end.x = start.x; - } else if start.y.is(end.y) { + } else if approx_eq(start.y, end.y) { start.y = self.known_y.inset(start.y); end.y = start.y; } @@ -174,9 +169,9 @@ impl<'w, 's> InsetGizmo<'w, 's> { } pub(super) fn rect_2d(&mut self, rect: LayoutRect, color: Color) { let (left, right, top, bottom) = rect_border_axis(rect); - if left.is(right) { + if approx_eq(left, right) { self.line_2d(Vec2::new(left, top), Vec2::new(left, bottom), color); - } else if top.is(bottom) { + } else if approx_eq(top, bottom) { self.line_2d(Vec2::new(left, top), Vec2::new(right, top), color); } else { let inset_x = |v| self.known_x.inset(v); From 5fc4458d75a67a2bf30c4c7c300dc32cb8790f4d Mon Sep 17 00:00:00 2001 From: pablo-lua Date: Sun, 10 Mar 2024 19:24:21 -0300 Subject: [PATCH 44/45] [alt] Fixed CI --- crates/bevy_dev_tools/src/debug_overlay/mod.rs | 2 +- docs/cargo_features.md | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/crates/bevy_dev_tools/src/debug_overlay/mod.rs b/crates/bevy_dev_tools/src/debug_overlay/mod.rs index f6533c6955841..952539850638d 100644 --- a/crates/bevy_dev_tools/src/debug_overlay/mod.rs +++ b/crates/bevy_dev_tools/src/debug_overlay/mod.rs @@ -10,7 +10,7 @@ use bevy_gizmos::{config::GizmoConfigStore, prelude::Gizmos, AppGizmoBuilder}; use bevy_hierarchy::{Children, Parent}; use bevy_math::{Vec2, Vec3Swizzles}; use bevy_render::{ - camera::{ClearColorConfig, RenderTarget}, + camera::RenderTarget, prelude::*, view::{RenderLayers, VisibilitySystems}, }; diff --git a/docs/cargo_features.md b/docs/cargo_features.md index f250553da91bd..c5bf29bd20c84 100644 --- a/docs/cargo_features.md +++ b/docs/cargo_features.md @@ -52,7 +52,6 @@ The default feature set enables most of the expected features of a game engine, |bevy_ci_testing|Enable systems that allow for automated testing on CI| |bevy_dev_tools|Provides a collection of developer tools| |bevy_dynamic_plugin|Plugin for dynamic loading (using [libloading](https://crates.io/crates/libloading))| -|bevy_ui_debug|Enable the bevy_ui debug overlay| |bmp|BMP image format support| |dds|DDS compressed texture support| |debug_glam_assert|Enable assertions in debug builds to check the validity of parameters passed to glam| From 2cfffd857e578c720e029f784eb326bf0a798ba6 Mon Sep 17 00:00:00 2001 From: Pablo Reinhardt Date: Mon, 18 Mar 2024 14:59:44 -0300 Subject: [PATCH 45/45] [fix] Duplicate entry on dev_tools TOML --- crates/bevy_dev_tools/Cargo.toml | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/crates/bevy_dev_tools/Cargo.toml b/crates/bevy_dev_tools/Cargo.toml index 9de077f8fb5c6..62ab2c8fcc8ae 100644 --- a/crates/bevy_dev_tools/Cargo.toml +++ b/crates/bevy_dev_tools/Cargo.toml @@ -16,12 +16,15 @@ bevy_ui_debug = [] [dependencies] # bevy bevy_app = { path = "../bevy_app", version = "0.14.0-dev" } +bevy_asset = { path = "../bevy_asset", version = "0.14.0-dev" } bevy_color = { path = "../bevy_color", version = "0.14.0-dev" } bevy_core = { path = "../bevy_core", version = "0.14.0-dev" } bevy_core_pipeline = { path = "../bevy_core_pipeline", version = "0.14.0-dev" } +bevy_diagnostic = { path = "../bevy_diagnostic", version = "0.14.0-dev" } bevy_ecs = { path = "../bevy_ecs", version = "0.14.0-dev" } bevy_gizmos = { path = "../bevy_gizmos", version = "0.14.0-dev" } bevy_hierarchy = { path = "../bevy_hierarchy", version = "0.14.0-dev" } +bevy_input = { path = "../bevy_input", version = "0.14.0-dev" } bevy_math = { path = "../bevy_math", version = "0.14.0-dev" } bevy_reflect = { path = "../bevy_reflect", version = "0.14.0-dev" } bevy_render = { path = "../bevy_render", version = "0.14.0-dev" } @@ -30,12 +33,7 @@ bevy_transform = { path = "../bevy_transform", version = "0.14.0-dev" } bevy_ui = { path = "../bevy_ui", version = "0.14.0-dev" } bevy_utils = { path = "../bevy_utils", version = "0.14.0-dev" } bevy_window = { path = "../bevy_window", version = "0.14.0-dev" } -bevy_asset = { path = "../bevy_asset", version = "0.14.0-dev" } -bevy_ui = { path = "../bevy_ui", version = "0.14.0-dev" } bevy_text = { path = "../bevy_text", version = "0.14.0-dev" } -bevy_diagnostic = { path = "../bevy_diagnostic", version = "0.14.0-dev" } -bevy_color = { path = "../bevy_color", version = "0.14.0-dev" } -bevy_input = { path = "../bevy_input", version = "0.14.0-dev" } # other serde = { version = "1.0", features = ["derive"], optional = true }