Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Merged by Bors] - Change UI coordinate system to have origin at top left corner #6000

Closed
wants to merge 13 commits into from
Closed
9 changes: 5 additions & 4 deletions crates/bevy_text/src/glyph_brush.rs
Original file line number Diff line number Diff line change
Expand Up @@ -73,16 +73,17 @@ impl GlyphBrush {
})
.collect::<Result<Vec<_>, _>>()?;

let mut max_y = std::f32::MIN;
let mut min_x = std::f32::MAX;
let mut min_y = std::f32::MAX;
for sg in &glyphs {
let glyph = &sg.glyph;

let scaled_font = sections_data[sg.section_index].3;
max_y = max_y.max(glyph.position.y - scaled_font.descent());
min_x = min_x.min(glyph.position.x);
min_y = min_y.min(glyph.position.y - scaled_font.ascent());
}
max_y = max_y.floor();
min_x = min_x.floor();
min_y = min_y.floor();

let mut positioned_glyphs = Vec::new();
for sg in glyphs {
Expand Down Expand Up @@ -119,7 +120,7 @@ impl GlyphBrush {
let size = Vec2::new(glyph_rect.width(), glyph_rect.height());

let x = bounds.min.x + size.x / 2.0 - min_x;
let y = max_y - bounds.max.y + size.y / 2.0;
let y = bounds.min.y + size.y / 2.0 - min_y;
let position = adjust.position(Vec2::new(x, y));

positioned_glyphs.push(PositionedGlyph {
Expand Down
5 changes: 2 additions & 3 deletions crates/bevy_ui/src/flex/convert.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,8 @@ pub fn from_rect(
taffy::geometry::Rect {
start: from_val(scale_factor, rect.left),
end: from_val(scale_factor, rect.right),
// NOTE: top and bottom are intentionally flipped. stretch has a flipped y-axis
top: from_val(scale_factor, rect.bottom),
bottom: from_val(scale_factor, rect.top),
top: from_val(scale_factor, rect.top),
bottom: from_val(scale_factor, rect.bottom),
}
}

Expand Down
2 changes: 1 addition & 1 deletion crates/bevy_ui/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
//! This crate contains Bevy's UI system, which can be used to create UI for both 2D and 3D games
//! # Basic usage
//! Spawn UI elements with [`entity::ButtonBundle`], [`entity::ImageBundle`], [`entity::TextBundle`] and [`entity::NodeBundle`]
//! This UI is laid out with the Flexbox paradigm (see <https://cssreference.io/flexbox/> ) except the vertical axis is inverted
//! This UI is laid out with the Flexbox paradigm (see <https://cssreference.io/flexbox/>)
mod flex;
mod focus;
mod geometry;
Expand Down
29 changes: 12 additions & 17 deletions crates/bevy_ui/src/render/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ use bevy_ecs::prelude::*;
use bevy_math::{Mat4, Rect, UVec4, Vec2, Vec3, Vec4Swizzles};
use bevy_reflect::TypeUuid;
use bevy_render::{
camera::{Camera, CameraProjection, OrthographicProjection, WindowOrigin},
camera::Camera,
color::Color,
render_asset::RenderAssets,
render_graph::{RenderGraph, RunGraphOnViewNode, SlotInfo, SlotType},
Expand Down Expand Up @@ -243,15 +243,11 @@ pub fn extract_default_ui_camera_view<T: Component>(
camera.physical_viewport_rect(),
camera.physical_viewport_size(),
) {
let mut projection = OrthographicProjection {
far: UI_CAMERA_FAR,
window_origin: WindowOrigin::BottomLeft,
..Default::default()
};
projection.update(logical_size.x, logical_size.y);
let projection_matrix =
Mat4::orthographic_rh(0.0, logical_size.x, logical_size.y, 0.0, 0.0, UI_CAMERA_FAR);
mahulst marked this conversation as resolved.
Show resolved Hide resolved
let default_camera_view = commands
.spawn(ExtractedView {
projection: projection.get_projection_matrix(),
projection: projection_matrix,
transform: GlobalTransform::from_xyz(
0.0,
0.0,
Expand Down Expand Up @@ -464,24 +460,23 @@ pub fn prepare_uinodes(
}
}

// Clip UVs (Note: y is reversed in UV space)
let atlas_extent = extracted_uinode.atlas_size.unwrap_or(uinode_rect.max);
let uvs = [
Vec2::new(
uinode_rect.min.x + positions_diff[0].x,
uinode_rect.max.y - positions_diff[0].y,
),
Vec2::new(
uinode_rect.max.x + positions_diff[1].x,
uinode_rect.max.y - positions_diff[1].y,
uinode_rect.min.x + positions_diff[3].x,
uinode_rect.min.y - positions_diff[3].y,
),
Vec2::new(
uinode_rect.max.x + positions_diff[2].x,
uinode_rect.min.y - positions_diff[2].y,
),
Vec2::new(
uinode_rect.min.x + positions_diff[3].x,
uinode_rect.min.y - positions_diff[3].y,
uinode_rect.max.x + positions_diff[1].x,
uinode_rect.max.y - positions_diff[1].y,
),
Vec2::new(
uinode_rect.min.x + positions_diff[0].x,
uinode_rect.max.y - positions_diff[0].y,
),
]
.map(|pos| pos / atlas_extent);
Expand Down
4 changes: 2 additions & 2 deletions crates/bevy_ui/src/ui_node.rs
Original file line number Diff line number Diff line change
Expand Up @@ -303,11 +303,11 @@ pub enum FlexDirection {
/// Same way as text direction along the main axis
#[default]
Row,
/// Flex from bottom to top
/// Flex from top to bottom
Column,
/// Opposite way as text direction along the main axis
RowReverse,
/// Flex from top to bottom
/// Flex from bottom to top
ColumnReverse,
}

Expand Down
14 changes: 3 additions & 11 deletions crates/bevy_winit/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -149,12 +149,9 @@ fn change_window(
}
bevy_window::WindowCommand::SetCursorPosition { position } => {
let window = winit_windows.get_window(id).unwrap();
let inner_size = window.inner_size().to_logical::<f32>(window.scale_factor());

window
.set_cursor_position(LogicalPosition::new(
position.x,
inner_size.height - position.y,
))
.set_cursor_position(LogicalPosition::new(position.x, position.y))
.unwrap_or_else(|e| error!("Unable to set cursor position: {}", e));
}
bevy_window::WindowCommand::SetMaximized { maximized } => {
Expand Down Expand Up @@ -431,13 +428,8 @@ pub fn winit_runner_with(mut app: App) {
}
WindowEvent::CursorMoved { position, .. } => {
let mut cursor_moved_events = world.resource_mut::<Events<CursorMoved>>();
let winit_window = winit_windows.get_window(window_id).unwrap();
let inner_size = winit_window.inner_size();

// move origin to bottom left
let y_position = inner_size.height as f64 - position.y;

let physical_position = DVec2::new(position.x, y_position);
let physical_position = DVec2::new(position.x, position.y);
window
.update_cursor_physical_position_from_backend(Some(physical_position));

Expand Down
31 changes: 23 additions & 8 deletions examples/ui/font_atlas_debug.rs
Original file line number Diff line number Diff line change
Expand Up @@ -82,12 +82,27 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>, mut state: ResM
let font_handle = asset_server.load("fonts/FiraSans-Bold.ttf");
state.handle = font_handle.clone();
commands.spawn(Camera2dBundle::default());
commands.spawn(TextBundle::from_section(
"a",
TextStyle {
font: font_handle,
font_size: 60.0,
color: Color::YELLOW,
},
));
commands
.spawn(NodeBundle {
background_color: Color::NONE.into(),
style: Style {
position_type: PositionType::Absolute,
position: UiRect {
bottom: Val::Px(0.0),
..default()
},
..default()
},
..default()
})
.with_children(|parent| {
parent.spawn(TextBundle::from_section(
"a",
TextStyle {
font: font_handle,
font_size: 60.0,
color: Color::YELLOW,
},
));
});
}
3 changes: 1 addition & 2 deletions examples/ui/text.rs
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,6 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
.with_text_alignment(TextAlignment::TOP_CENTER)
// Set the style of the TextBundle itself.
.with_style(Style {
align_self: AlignSelf::FlexEnd,
mahulst marked this conversation as resolved.
Show resolved Hide resolved
position_type: PositionType::Absolute,
position: UiRect {
bottom: Val::Px(5.0),
Expand Down Expand Up @@ -74,7 +73,7 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
}),
])
.with_style(Style {
align_self: AlignSelf::FlexEnd,
align_self: AlignSelf::FlexStart,
mahulst marked this conversation as resolved.
Show resolved Hide resolved
..default()
}),
FpsText,
Expand Down
4 changes: 1 addition & 3 deletions examples/ui/text_debug.rs
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ fn infotext_system(mut commands: Commands, asset_server: Res<AssetServer>) {
},
)
.with_style(Style {
align_self: AlignSelf::FlexEnd,
align_self: AlignSelf::FlexStart,
mahulst marked this conversation as resolved.
Show resolved Hide resolved
position_type: PositionType::Absolute,
position: UiRect {
top: Val::Px(5.0),
Expand All @@ -55,7 +55,6 @@ fn infotext_system(mut commands: Commands, asset_server: Res<AssetServer>) {
)
.with_text_alignment(TextAlignment::CENTER)
.with_style(Style {
align_self: AlignSelf::FlexEnd,
position_type: PositionType::Absolute,
position: UiRect {
top: Val::Px(5.0),
Expand Down Expand Up @@ -115,7 +114,6 @@ fn infotext_system(mut commands: Commands, asset_server: Res<AssetServer>) {
),
])
.with_style(Style {
align_self: AlignSelf::FlexEnd,
position_type: PositionType::Absolute,
position: UiRect {
bottom: Val::Px(5.0),
Expand Down
15 changes: 7 additions & 8 deletions examples/ui/ui.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
.spawn(NodeBundle {
style: Style {
size: Size::new(Val::Percent(100.0), Val::Percent(100.0)),
align_items: AlignItems::FlexEnd,
align_items: AlignItems::FlexStart,
mahulst marked this conversation as resolved.
Show resolved Hide resolved
..default()
},
background_color: Color::rgb(0.15, 0.15, 0.15).into(),
Expand Down Expand Up @@ -77,7 +77,7 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
parent
.spawn(NodeBundle {
style: Style {
flex_direction: FlexDirection::ColumnReverse,
flex_direction: FlexDirection::Column,
justify_content: JustifyContent::Center,
size: Size::new(Val::Px(200.0), Val::Percent(100.0)),
..default()
Expand Down Expand Up @@ -110,7 +110,7 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
parent
.spawn(NodeBundle {
style: Style {
flex_direction: FlexDirection::ColumnReverse,
flex_direction: FlexDirection::Column,
align_self: AlignSelf::Center,
size: Size::new(Val::Percent(100.0), Val::Percent(50.0)),
overflow: Overflow::Hidden,
Expand All @@ -125,7 +125,7 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
.spawn((
NodeBundle {
style: Style {
flex_direction: FlexDirection::ColumnReverse,
flex_direction: FlexDirection::Column,
flex_grow: 1.0,
max_size: Size::UNDEFINED,
..default()
Expand Down Expand Up @@ -163,7 +163,6 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
});
});
});
// absolute positioning
parent
.spawn(NodeBundle {
style: Style {
Expand Down Expand Up @@ -280,7 +279,7 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
size: Size::new(Val::Percent(100.0), Val::Percent(100.0)),
position_type: PositionType::Absolute,
justify_content: JustifyContent::Center,
align_items: AlignItems::FlexEnd,
align_items: AlignItems::FlexStart,
mahulst marked this conversation as resolved.
Show resolved Hide resolved
..default()
},
background_color: Color::NONE.into(),
Expand Down Expand Up @@ -322,8 +321,8 @@ fn mouse_scroll(
MouseScrollUnit::Line => mouse_wheel_event.y * 20.,
MouseScrollUnit::Pixel => mouse_wheel_event.y,
};
scrolling_list.position += dy;
scrolling_list.position = scrolling_list.position.clamp(-max_scroll, 0.);
scrolling_list.position -= dy;
scrolling_list.position = scrolling_list.position.clamp(0., max_scroll);
style.position.top = Val::Px(scrolling_list.position);
}
}
Expand Down