mirror of
https://github.com/kristoferssolo/maze-ascension.git
synced 2025-12-30 13:21:38 +00:00
Merge pull request #21 from kristoferssolo/feat/UI
This commit is contained in:
commit
285d35d87e
@ -309,7 +309,6 @@ pub enum Screen {
|
|||||||
Splash,
|
Splash,
|
||||||
Loading,
|
Loading,
|
||||||
Title,
|
Title,
|
||||||
Credits,
|
|
||||||
Gameplay,
|
Gameplay,
|
||||||
Victory,
|
Victory,
|
||||||
Leaderboard,
|
Leaderboard,
|
||||||
|
|||||||
@ -2,3 +2,4 @@ pub const MOVEMENT_THRESHOLD: f32 = 0.01;
|
|||||||
pub const WALL_OVERLAP_MODIFIER: f32 = 1.25;
|
pub const WALL_OVERLAP_MODIFIER: f32 = 1.25;
|
||||||
pub const FLOOR_Y_OFFSET: u8 = 200;
|
pub const FLOOR_Y_OFFSET: u8 = 200;
|
||||||
pub const MOVEMENT_COOLDOWN: f32 = 1.0; // one second cooldown
|
pub const MOVEMENT_COOLDOWN: f32 = 1.0; // one second cooldown
|
||||||
|
pub const TITLE: &'static str = "Maze Ascension: The Labyrinth of Echoes";
|
||||||
|
|||||||
@ -1,7 +1,8 @@
|
|||||||
use crate::{
|
use crate::{
|
||||||
floor::components::{CurrentFloor, Floor},
|
floor::components::{CurrentFloor, Floor},
|
||||||
maze::{components::MazeConfig, events::RespawnMaze, GlobalMazeConfig, MazePluginLoaded},
|
maze::{components::MazeConfig, events::RespawnMaze, GlobalMazeConfig},
|
||||||
player::events::RespawnPlayer,
|
player::events::RespawnPlayer,
|
||||||
|
screens::Screen,
|
||||||
};
|
};
|
||||||
use bevy::{prelude::*, window::PrimaryWindow};
|
use bevy::{prelude::*, window::PrimaryWindow};
|
||||||
use bevy_egui::{
|
use bevy_egui::{
|
||||||
@ -13,9 +14,12 @@ use rand::{thread_rng, Rng};
|
|||||||
use std::ops::RangeInclusive;
|
use std::ops::RangeInclusive;
|
||||||
|
|
||||||
pub fn maze_controls_ui(world: &mut World) {
|
pub fn maze_controls_ui(world: &mut World) {
|
||||||
if world.get_resource::<MazePluginLoaded>().is_none() {
|
if let Some(state) = world.get_resource::<State<Screen>>() {
|
||||||
|
// Check if the current state is NOT Gameplay
|
||||||
|
if *state.get() != Screen::Gameplay {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
let Ok(egui_context) = world
|
let Ok(egui_context) = world
|
||||||
.query_filtered::<&mut EguiContext, With<PrimaryWindow>>()
|
.query_filtered::<&mut EguiContext, With<PrimaryWindow>>()
|
||||||
|
|||||||
@ -2,7 +2,7 @@ mod despawn;
|
|||||||
mod movement;
|
mod movement;
|
||||||
mod spawn;
|
mod spawn;
|
||||||
|
|
||||||
use crate::maze::MazePluginLoaded;
|
use crate::screens::Screen;
|
||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
use despawn::despawn_floor;
|
use despawn::despawn_floor;
|
||||||
use movement::{handle_floor_transition_events, move_floors};
|
use movement::{handle_floor_transition_events, move_floors};
|
||||||
@ -18,6 +18,6 @@ pub(super) fn plugin(app: &mut App) {
|
|||||||
move_floors,
|
move_floors,
|
||||||
)
|
)
|
||||||
.chain()
|
.chain()
|
||||||
.run_if(resource_exists::<MazePluginLoaded>),
|
.run_if(in_state(Screen::Gameplay)),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -33,7 +33,7 @@ pub(super) fn spawn_floor(
|
|||||||
floor: target_floor,
|
floor: target_floor,
|
||||||
config: MazeConfig {
|
config: MazeConfig {
|
||||||
start_pos: config.end_pos,
|
start_pos: config.end_pos,
|
||||||
radius: config.radius + 2,
|
radius: config.radius + 1,
|
||||||
..default()
|
..default()
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@ -14,6 +14,7 @@ use bevy::{
|
|||||||
audio::{AudioPlugin, Volume},
|
audio::{AudioPlugin, Volume},
|
||||||
prelude::*,
|
prelude::*,
|
||||||
};
|
};
|
||||||
|
use constants::TITLE;
|
||||||
use theme::{palette::rose_pine, prelude::ColorScheme};
|
use theme::{palette::rose_pine, prelude::ColorScheme};
|
||||||
|
|
||||||
pub struct AppPlugin;
|
pub struct AppPlugin;
|
||||||
@ -41,7 +42,7 @@ impl Plugin for AppPlugin {
|
|||||||
})
|
})
|
||||||
.set(WindowPlugin {
|
.set(WindowPlugin {
|
||||||
primary_window: Window {
|
primary_window: Window {
|
||||||
title: "Maze Ascension: The Labyrinth of Echoes".to_string(),
|
title: TITLE.to_string(),
|
||||||
canvas: Some("#bevy".to_string()),
|
canvas: Some("#bevy".to_string()),
|
||||||
fit_canvas_to_parent: true,
|
fit_canvas_to_parent: true,
|
||||||
prevent_default_event_handling: true,
|
prevent_default_event_handling: true,
|
||||||
@ -103,9 +104,6 @@ fn spawn_camera(mut commands: Commands) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn load_background(mut commands: Commands) {
|
fn load_background(mut commands: Commands) {
|
||||||
#[cfg(feature = "dev")]
|
|
||||||
let colorcheme = rose_pine::RosePine::Base;
|
|
||||||
#[cfg(not(feature = "dev"))]
|
|
||||||
let colorcheme = rose_pine::RosePineDawn::Base;
|
let colorcheme = rose_pine::RosePineDawn::Base;
|
||||||
commands.insert_resource(ClearColor(colorcheme.to_color()));
|
commands.insert_resource(ClearColor(colorcheme.to_color()));
|
||||||
}
|
}
|
||||||
|
|||||||
@ -79,7 +79,7 @@ impl MazeConfig {
|
|||||||
impl Default for MazeConfig {
|
impl Default for MazeConfig {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self::new(
|
Self::new(
|
||||||
8,
|
4,
|
||||||
HexOrientation::Flat,
|
HexOrientation::Flat,
|
||||||
None,
|
None,
|
||||||
&GlobalMazeConfig::default(),
|
&GlobalMazeConfig::default(),
|
||||||
@ -93,7 +93,6 @@ fn generate_pos<R: Rng>(radius: u16, rng: &mut R) -> Hex {
|
|||||||
loop {
|
loop {
|
||||||
let q = rng.gen_range(-radius..=radius);
|
let q = rng.gen_range(-radius..=radius);
|
||||||
let r = rng.gen_range(-radius..=radius);
|
let r = rng.gen_range(-radius..=radius);
|
||||||
|
|
||||||
let s = -q - r; // Calculate third coordinate (axial coordinates: q + r + s = 0)
|
let s = -q - r; // Calculate third coordinate (axial coordinates: q + r + s = 0)
|
||||||
|
|
||||||
// Check if the position is within the hexagonal radius
|
// Check if the position is within the hexagonal radius
|
||||||
|
|||||||
@ -9,7 +9,7 @@ pub mod triggers;
|
|||||||
use bevy::{ecs::system::RunSystemOnce, prelude::*};
|
use bevy::{ecs::system::RunSystemOnce, prelude::*};
|
||||||
use components::HexMaze;
|
use components::HexMaze;
|
||||||
use events::{DespawnMaze, RespawnMaze, SpawnMaze};
|
use events::{DespawnMaze, RespawnMaze, SpawnMaze};
|
||||||
pub use resources::{GlobalMazeConfig, MazePluginLoaded};
|
pub use resources::GlobalMazeConfig;
|
||||||
|
|
||||||
pub(super) fn plugin(app: &mut App) {
|
pub(super) fn plugin(app: &mut App) {
|
||||||
app.init_resource::<GlobalMazeConfig>()
|
app.init_resource::<GlobalMazeConfig>()
|
||||||
@ -22,5 +22,4 @@ pub(super) fn plugin(app: &mut App) {
|
|||||||
|
|
||||||
pub fn spawn_level_command(world: &mut World) {
|
pub fn spawn_level_command(world: &mut World) {
|
||||||
let _ = world.run_system_once(systems::setup::setup);
|
let _ = world.run_system_once(systems::setup::setup);
|
||||||
world.insert_resource(MazePluginLoaded);
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,9 +1,5 @@
|
|||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
|
|
||||||
#[derive(Debug, Default, Reflect, Resource)]
|
|
||||||
#[reflect(Resource)]
|
|
||||||
pub struct MazePluginLoaded;
|
|
||||||
|
|
||||||
#[derive(Debug, Reflect, Resource, Clone)]
|
#[derive(Debug, Reflect, Resource, Clone)]
|
||||||
#[reflect(Resource)]
|
#[reflect(Resource)]
|
||||||
pub struct GlobalMazeConfig {
|
pub struct GlobalMazeConfig {
|
||||||
|
|||||||
@ -8,6 +8,7 @@ use crate::{
|
|||||||
events::SpawnMaze,
|
events::SpawnMaze,
|
||||||
resources::GlobalMazeConfig,
|
resources::GlobalMazeConfig,
|
||||||
},
|
},
|
||||||
|
screens::Screen,
|
||||||
theme::palette::rose_pine::RosePineDawn,
|
theme::palette::rose_pine::RosePineDawn,
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -53,6 +54,7 @@ pub(crate) fn spawn_maze(
|
|||||||
config.clone(),
|
config.clone(),
|
||||||
Transform::from_translation(Vec3::ZERO.with_y(y_offset)),
|
Transform::from_translation(Vec3::ZERO.with_y(y_offset)),
|
||||||
Visibility::Visible,
|
Visibility::Visible,
|
||||||
|
StateScoped(Screen::Gameplay),
|
||||||
))
|
))
|
||||||
.insert_if(CurrentFloor, || *floor == 1)
|
.insert_if(CurrentFloor, || *floor == 1)
|
||||||
.id();
|
.id();
|
||||||
|
|||||||
@ -222,6 +222,7 @@ impl From<LogicalDirection> for EdgeDirection {
|
|||||||
direction.rotate_cw(0)
|
direction.rotate_cw(0)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use super::*;
|
use super::*;
|
||||||
|
|||||||
@ -3,7 +3,7 @@ mod movement;
|
|||||||
pub mod setup;
|
pub mod setup;
|
||||||
mod vertical_transition;
|
mod vertical_transition;
|
||||||
|
|
||||||
use crate::maze::MazePluginLoaded;
|
use crate::screens::Screen;
|
||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
use input::player_input;
|
use input::player_input;
|
||||||
use movement::player_movement;
|
use movement::player_movement;
|
||||||
@ -17,6 +17,6 @@ pub(super) fn plugin(app: &mut App) {
|
|||||||
player_movement.after(player_input),
|
player_movement.after(player_input),
|
||||||
handle_floor_transition,
|
handle_floor_transition,
|
||||||
)
|
)
|
||||||
.run_if(resource_exists::<MazePluginLoaded>),
|
.run_if(in_state(Screen::Gameplay)),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -6,6 +6,7 @@ use crate::{
|
|||||||
components::{CurrentPosition, Player},
|
components::{CurrentPosition, Player},
|
||||||
events::SpawnPlayer,
|
events::SpawnPlayer,
|
||||||
},
|
},
|
||||||
|
screens::Screen,
|
||||||
};
|
};
|
||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
|
|
||||||
@ -34,5 +35,6 @@ pub(super) fn spawn_player(
|
|||||||
Mesh3d(meshes.add(generate_pill_mesh(player_radius, player_height / 2.))),
|
Mesh3d(meshes.add(generate_pill_mesh(player_radius, player_height / 2.))),
|
||||||
MeshMaterial3d(materials.add(blue_material())),
|
MeshMaterial3d(materials.add(blue_material())),
|
||||||
Transform::from_xyz(start_pos.x, y_offset, start_pos.y),
|
Transform::from_xyz(start_pos.x, y_offset, start_pos.y),
|
||||||
|
StateScoped(Screen::Gameplay),
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,71 +0,0 @@
|
|||||||
//! A credits screen that can be accessed from the title screen.
|
|
||||||
|
|
||||||
use bevy::prelude::*;
|
|
||||||
|
|
||||||
use crate::{asset_tracking::LoadResource, audio::Music, screens::Screen, theme::prelude::*};
|
|
||||||
|
|
||||||
pub(super) fn plugin(app: &mut App) {
|
|
||||||
app.add_systems(OnEnter(Screen::Credits), spawn_credits_screen);
|
|
||||||
|
|
||||||
app.load_resource::<CreditsMusic>();
|
|
||||||
app.add_systems(OnEnter(Screen::Credits), play_credits_music);
|
|
||||||
app.add_systems(OnExit(Screen::Credits), stop_music);
|
|
||||||
}
|
|
||||||
|
|
||||||
fn spawn_credits_screen(mut commands: Commands) {
|
|
||||||
commands
|
|
||||||
.ui_root()
|
|
||||||
.insert(StateScoped(Screen::Credits))
|
|
||||||
.with_children(|children| {
|
|
||||||
children.header("Made by");
|
|
||||||
children.label("Joe Shmoe - Implemented aligator wrestling AI");
|
|
||||||
children.label("Jane Doe - Made the music for the alien invasion");
|
|
||||||
|
|
||||||
children.header("Assets");
|
|
||||||
children.label("Bevy logo - All rights reserved by the Bevy Foundation. Permission granted for splash screen use when unmodified.");
|
|
||||||
children.label("Ducky sprite - CC0 by Caz Creates Games");
|
|
||||||
children.label("Button SFX - CC0 by Jaszunio15");
|
|
||||||
children.label("Music - CC BY 3.0 by Kevin MacLeod");
|
|
||||||
|
|
||||||
children.button("Back").observe(enter_title_screen);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
fn enter_title_screen(_trigger: Trigger<OnPress>, mut next_screen: ResMut<NextState<Screen>>) {
|
|
||||||
next_screen.set(Screen::Title);
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Resource, Asset, Reflect, Clone)]
|
|
||||||
pub struct CreditsMusic {
|
|
||||||
#[dependency]
|
|
||||||
music: Handle<AudioSource>,
|
|
||||||
entity: Option<Entity>,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl FromWorld for CreditsMusic {
|
|
||||||
fn from_world(world: &mut World) -> Self {
|
|
||||||
let assets = world.resource::<AssetServer>();
|
|
||||||
Self {
|
|
||||||
music: assets.load("audio/music/Monkeys Spinning Monkeys.ogg"),
|
|
||||||
entity: None,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn play_credits_music(mut commands: Commands, mut music: ResMut<CreditsMusic>) {
|
|
||||||
music.entity = Some(
|
|
||||||
commands
|
|
||||||
.spawn((
|
|
||||||
AudioPlayer::<AudioSource>(music.music.clone()),
|
|
||||||
PlaybackSettings::LOOP,
|
|
||||||
Music,
|
|
||||||
))
|
|
||||||
.id(),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
fn stop_music(mut commands: Commands, mut music: ResMut<CreditsMusic>) {
|
|
||||||
if let Some(entity) = music.entity.take() {
|
|
||||||
commands.entity(entity).despawn_recursive();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@ -4,7 +4,7 @@
|
|||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
screens::{credits::CreditsMusic, gameplay::GameplayMusic, Screen},
|
screens::{gameplay::GameplayMusic, Screen},
|
||||||
theme::{interaction::InteractionAssets, prelude::*},
|
theme::{interaction::InteractionAssets, prelude::*},
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -21,8 +21,8 @@ fn spawn_loading_screen(mut commands: Commands) {
|
|||||||
commands
|
commands
|
||||||
.ui_root()
|
.ui_root()
|
||||||
.insert(StateScoped(Screen::Loading))
|
.insert(StateScoped(Screen::Loading))
|
||||||
.with_children(|children| {
|
.with_children(|parent| {
|
||||||
children.label("Loading...").insert(Node {
|
parent.label("Loading...").insert(Node {
|
||||||
justify_content: JustifyContent::Center,
|
justify_content: JustifyContent::Center,
|
||||||
..default()
|
..default()
|
||||||
});
|
});
|
||||||
@ -35,8 +35,7 @@ fn continue_to_title_screen(mut next_screen: ResMut<NextState<Screen>>) {
|
|||||||
|
|
||||||
const fn all_assets_loaded(
|
const fn all_assets_loaded(
|
||||||
interaction_assets: Option<Res<InteractionAssets>>,
|
interaction_assets: Option<Res<InteractionAssets>>,
|
||||||
credits_music: Option<Res<CreditsMusic>>,
|
|
||||||
gameplay_music: Option<Res<GameplayMusic>>,
|
gameplay_music: Option<Res<GameplayMusic>>,
|
||||||
) -> bool {
|
) -> bool {
|
||||||
interaction_assets.is_some() && credits_music.is_some() && gameplay_music.is_some()
|
interaction_assets.is_some() && gameplay_music.is_some()
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,6 +1,5 @@
|
|||||||
//! The game's main screen states and transitions between them.
|
//! The game's main screen states and transitions between them.
|
||||||
|
|
||||||
mod credits;
|
|
||||||
mod gameplay;
|
mod gameplay;
|
||||||
mod loading;
|
mod loading;
|
||||||
mod splash;
|
mod splash;
|
||||||
@ -13,7 +12,6 @@ pub(super) fn plugin(app: &mut App) {
|
|||||||
app.enable_state_scoped_entities::<Screen>();
|
app.enable_state_scoped_entities::<Screen>();
|
||||||
|
|
||||||
app.add_plugins((
|
app.add_plugins((
|
||||||
credits::plugin,
|
|
||||||
gameplay::plugin,
|
gameplay::plugin,
|
||||||
loading::plugin,
|
loading::plugin,
|
||||||
splash::plugin,
|
splash::plugin,
|
||||||
@ -29,6 +27,5 @@ pub enum Screen {
|
|||||||
#[cfg_attr(feature = "dev", default)]
|
#[cfg_attr(feature = "dev", default)]
|
||||||
Loading,
|
Loading,
|
||||||
Title,
|
Title,
|
||||||
Credits,
|
|
||||||
Gameplay,
|
Gameplay,
|
||||||
}
|
}
|
||||||
|
|||||||
@ -12,12 +12,19 @@ fn spawn_title_screen(mut commands: Commands) {
|
|||||||
commands
|
commands
|
||||||
.ui_root()
|
.ui_root()
|
||||||
.insert(StateScoped(Screen::Title))
|
.insert(StateScoped(Screen::Title))
|
||||||
.with_children(|children| {
|
.with_children(|parent| {
|
||||||
children.button("Play").observe(enter_gameplay_screen);
|
parent
|
||||||
children.button("Credits").observe(enter_credits_screen);
|
.spawn(Node {
|
||||||
|
bottom: Val::Px(70.),
|
||||||
|
..default()
|
||||||
|
})
|
||||||
|
.with_children(|parent| {
|
||||||
|
parent.header("Maze Ascension");
|
||||||
|
});
|
||||||
|
parent.button("Play").observe(enter_gameplay_screen);
|
||||||
|
|
||||||
#[cfg(not(target_family = "wasm"))]
|
#[cfg(not(target_family = "wasm"))]
|
||||||
children.button("Exit").observe(exit_app);
|
parent.button("Quit").observe(exit_app);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -25,10 +32,6 @@ fn enter_gameplay_screen(_trigger: Trigger<OnPress>, mut next_screen: ResMut<Nex
|
|||||||
next_screen.set(Screen::Gameplay);
|
next_screen.set(Screen::Gameplay);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn enter_credits_screen(_trigger: Trigger<OnPress>, mut next_screen: ResMut<NextState<Screen>>) {
|
|
||||||
next_screen.set(Screen::Credits);
|
|
||||||
}
|
|
||||||
|
|
||||||
#[cfg(not(target_family = "wasm"))]
|
#[cfg(not(target_family = "wasm"))]
|
||||||
fn exit_app(_trigger: Trigger<OnPress>, mut app_exit: EventWriter<AppExit>) {
|
fn exit_app(_trigger: Trigger<OnPress>, mut app_exit: EventWriter<AppExit>) {
|
||||||
app_exit.send(AppExit::Success);
|
app_exit.send(AppExit::Success);
|
||||||
|
|||||||
@ -2,15 +2,6 @@ pub mod rose_pine;
|
|||||||
|
|
||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
|
|
||||||
pub const BUTTON_HOVERED_BACKGROUND: Color = Color::srgb(0.186, 0.328, 0.573);
|
|
||||||
pub const BUTTON_PRESSED_BACKGROUND: Color = Color::srgb(0.286, 0.478, 0.773);
|
|
||||||
|
|
||||||
pub const BUTTON_TEXT: Color = Color::srgb(0.925, 0.925, 0.925);
|
|
||||||
pub const LABEL_TEXT: Color = Color::srgb(0.867, 0.827, 0.412);
|
|
||||||
pub const HEADER_TEXT: Color = Color::srgb(0.867, 0.827, 0.412);
|
|
||||||
|
|
||||||
pub const NODE_BACKGROUND: Color = Color::srgb(0.286, 0.478, 0.773);
|
|
||||||
|
|
||||||
const MAX_COLOR_VALUE: f32 = 255.;
|
const MAX_COLOR_VALUE: f32 = 255.;
|
||||||
|
|
||||||
pub(super) const fn rgb_u8(red: u8, green: u8, blue: u8) -> Color {
|
pub(super) const fn rgb_u8(red: u8, green: u8, blue: u8) -> Color {
|
||||||
|
|||||||
@ -1,7 +1,9 @@
|
|||||||
//! Helper traits for creating common widgets.
|
//! Helper traits for creating common widgets.
|
||||||
|
|
||||||
use bevy::{ecs::system::EntityCommands, prelude::*, ui::Val::*};
|
use bevy::{ecs::system::EntityCommands, prelude::*, ui::Val::*};
|
||||||
|
use rose_pine::RosePineDawn;
|
||||||
|
|
||||||
|
use super::prelude::ColorScheme;
|
||||||
use crate::theme::{interaction::InteractionPalette, palette::*};
|
use crate::theme::{interaction::InteractionPalette, palette::*};
|
||||||
|
|
||||||
/// An extension trait for spawning UI widgets.
|
/// An extension trait for spawning UI widgets.
|
||||||
@ -22,7 +24,7 @@ impl<T: SpawnUi> Widgets for T {
|
|||||||
Name::new("Button"),
|
Name::new("Button"),
|
||||||
Button,
|
Button,
|
||||||
ImageNode {
|
ImageNode {
|
||||||
color: NODE_BACKGROUND,
|
color: RosePineDawn::Surface.to_color(),
|
||||||
..default()
|
..default()
|
||||||
},
|
},
|
||||||
Node {
|
Node {
|
||||||
@ -30,23 +32,26 @@ impl<T: SpawnUi> Widgets for T {
|
|||||||
height: Px(65.0),
|
height: Px(65.0),
|
||||||
justify_content: JustifyContent::Center,
|
justify_content: JustifyContent::Center,
|
||||||
align_items: AlignItems::Center,
|
align_items: AlignItems::Center,
|
||||||
|
border: UiRect::all(Px(4.)),
|
||||||
..default()
|
..default()
|
||||||
},
|
},
|
||||||
|
BorderRadius::all(Px(8.)),
|
||||||
|
BorderColor(RosePineDawn::Text.to_color()),
|
||||||
InteractionPalette {
|
InteractionPalette {
|
||||||
none: NODE_BACKGROUND,
|
none: RosePineDawn::HighlightLow.to_color(),
|
||||||
hovered: BUTTON_HOVERED_BACKGROUND,
|
hovered: RosePineDawn::HighlightMed.to_color(),
|
||||||
pressed: BUTTON_PRESSED_BACKGROUND,
|
pressed: RosePineDawn::HighlightHigh.to_color(),
|
||||||
},
|
},
|
||||||
));
|
));
|
||||||
entity.with_children(|children| {
|
entity.with_children(|parent| {
|
||||||
children.spawn_ui((
|
parent.spawn_ui((
|
||||||
Name::new("Button Text"),
|
Name::new("Button Text"),
|
||||||
Text(text.into()),
|
Text(text.into()),
|
||||||
TextFont {
|
TextFont {
|
||||||
font_size: 40.0,
|
font_size: 40.0,
|
||||||
..default()
|
..default()
|
||||||
},
|
},
|
||||||
TextColor(BUTTON_TEXT),
|
TextColor(RosePineDawn::Text.to_color()),
|
||||||
));
|
));
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -63,38 +68,38 @@ impl<T: SpawnUi> Widgets for T {
|
|||||||
align_items: AlignItems::Center,
|
align_items: AlignItems::Center,
|
||||||
..default()
|
..default()
|
||||||
},
|
},
|
||||||
BackgroundColor(NODE_BACKGROUND),
|
|
||||||
));
|
));
|
||||||
entity.with_children(|children| {
|
entity.with_children(|parent| {
|
||||||
children.spawn_ui((
|
parent.spawn_ui((
|
||||||
Name::new("Header Text"),
|
Name::new("Header Text"),
|
||||||
Text(text.into()),
|
Text(text.into()),
|
||||||
TextFont {
|
TextFont {
|
||||||
font_size: 40.0,
|
font_size: 60.0,
|
||||||
..default()
|
..default()
|
||||||
},
|
},
|
||||||
TextColor(HEADER_TEXT),
|
TextLayout {
|
||||||
|
justify: JustifyText::Center,
|
||||||
|
..default()
|
||||||
|
},
|
||||||
|
TextColor(RosePineDawn::Text.to_color()),
|
||||||
));
|
));
|
||||||
});
|
});
|
||||||
entity
|
entity
|
||||||
}
|
}
|
||||||
|
|
||||||
fn label(&mut self, _text: impl Into<String>) -> EntityCommands {
|
fn label(&mut self, text: impl Into<String>) -> EntityCommands {
|
||||||
let entity = self.spawn_ui((
|
let entity = self.spawn_ui((
|
||||||
Name::new("Label"),
|
Name::new("Label"),
|
||||||
Text::default(),
|
Text(text.into()),
|
||||||
// TextBundle::from_section(
|
TextFont {
|
||||||
// text,
|
font_size: 24.0,
|
||||||
// TextStyle {
|
..default()
|
||||||
// font_size: 24.0,
|
},
|
||||||
// color: LABEL_TEXT,
|
TextColor(RosePineDawn::Text.to_color()),
|
||||||
// ..default()
|
Node {
|
||||||
// },
|
width: Px(500.),
|
||||||
// )
|
..default()
|
||||||
// .with_style(Style {
|
},
|
||||||
// width: Px(500.0),
|
|
||||||
// ..default()
|
|
||||||
// }),
|
|
||||||
));
|
));
|
||||||
entity
|
entity
|
||||||
}
|
}
|
||||||
@ -117,7 +122,7 @@ impl Containers for Commands<'_, '_> {
|
|||||||
justify_content: JustifyContent::Center,
|
justify_content: JustifyContent::Center,
|
||||||
align_items: AlignItems::Center,
|
align_items: AlignItems::Center,
|
||||||
flex_direction: FlexDirection::Column,
|
flex_direction: FlexDirection::Column,
|
||||||
row_gap: Px(10.0),
|
row_gap: Px(32.0),
|
||||||
position_type: PositionType::Absolute,
|
position_type: PositionType::Absolute,
|
||||||
..default()
|
..default()
|
||||||
},
|
},
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user