OffsetAlignment + PlayerMenu

This commit is contained in:
marceline-cramer 2022-07-27 21:21:24 -06:00
parent 0e546e8010
commit 447bd542af
2 changed files with 92 additions and 7 deletions

View File

@ -15,7 +15,7 @@ pub mod text;
use button::{Button, RectButton, RectButtonStyle, RoundButton, RoundButtonStyle};
use menu::{SlotMenu, SlotMenuEvent, TabMenu};
use scroll::{ScrollBar, ScrollView};
use shell::{Offset, Reveal};
use shell::{Offset, OffsetAlignment, Reveal};
use text::{HorizontalAlignment, Label, LabelText};
#[allow(unused)]
@ -45,6 +45,10 @@ impl<T: Widget> Widget for Option<T> {
}
}
pub trait RectBounds {
fn get_bounds(&self) -> Rect;
}
#[allow(unused)]
pub trait Container {
fn with_children(&mut self, f: impl FnMut(&mut dyn Widget));
@ -72,6 +76,7 @@ impl<T: Container> Widget for T {
pub struct MainMenu {
pub menu: Offset<SlotMenu<RoundButton>>,
pub player_info: Reveal<Offset<PlayerInfo>>,
pub inventory: Reveal<Offset<TabMenu>>,
pub settings: Reveal<Offset<SettingsMenu>>,
}
@ -108,10 +113,20 @@ impl Default for MainMenu {
let menu = SlotMenu::new(buttons, 0.18);
let menu = Offset::new(menu, Vec2::new(Self::POSITION_X, 0.0));
let submenu_spacing_right = Vec2::new(Self::SUBMENU_SPACING + Self::POSITION_X, 0.0);
let submenu_spacing_left = Vec2::new(Self::POSITION_X - Self::SUBMENU_SPACING, 0.0);
let submenu_spacing_right = Vec2::new(Self::POSITION_X + Self::SUBMENU_SPACING, 0.0);
let reveal_slide = -0.02;
let reveal_duration = 0.1;
let player_info = PlayerInfo::new();
let player_info = Offset::new_aligned(
player_info,
submenu_spacing_left,
OffsetAlignment::End,
OffsetAlignment::Center,
);
let player_info = Reveal::new(player_info, -reveal_slide, reveal_duration);
let inventory = TabMenu::new();
let inventory = Offset::new(inventory, submenu_spacing_right);
let inventory = Reveal::new(inventory, reveal_slide, reveal_duration);
@ -122,6 +137,7 @@ impl Default for MainMenu {
Self {
menu,
player_info,
inventory,
settings,
}
@ -131,6 +147,7 @@ impl Default for MainMenu {
impl Container for MainMenu {
fn with_children(&mut self, mut f: impl FnMut(&mut dyn Widget)) {
f(&mut self.menu);
f(&mut self.player_info);
f(&mut self.inventory);
f(&mut self.settings);
}
@ -143,8 +160,14 @@ impl Container for MainMenu {
};
match self.menu.get_event() {
SlotMenuEvent::SubmenuOpen(0) => self.inventory.show(),
SlotMenuEvent::SubmenuClose(0) => self.inventory.hide(),
SlotMenuEvent::SubmenuOpen(0) => {
self.player_info.show();
self.inventory.show();
}
SlotMenuEvent::SubmenuClose(0) => {
self.player_info.hide();
self.inventory.hide();
}
SlotMenuEvent::SubmenuOpen(4) => self.settings.show(),
SlotMenuEvent::SubmenuClose(4) => self.settings.hide(),
_ => {}
@ -152,6 +175,34 @@ impl Container for MainMenu {
}
}
pub struct PlayerInfo {
width: f32,
height: f32,
rounding: f32,
}
impl PlayerInfo {
pub fn new() -> Self {
Self {
width: 0.5,
height: 0.9,
rounding: 0.02,
}
}
}
impl RectBounds for PlayerInfo {
fn get_bounds(&self) -> Rect {
Rect::from_xy_size(Vec2::ZERO, Vec2::new(self.width, self.height))
}
}
impl Widget for PlayerInfo {
fn draw(&mut self, ctx: &DrawContext) {
ctx.draw_rounded_rect(self.get_bounds(), self.rounding, Color::WHITE);
}
}
pub struct Inventory {
width: f32,
height: f32,

View File

@ -1,7 +1,7 @@
use super::Widget;
use super::{RectBounds, Widget};
use crate::anim::Animation;
use crate::{CursorEventKind, Vec2};
use canary_script::draw::DrawContext;
use canary_script::draw::{DrawContext, Rect};
use keyframe::functions::*;
use std::ops::{Deref, DerefMut};
@ -89,6 +89,25 @@ impl<T: Widget> Widget for Reveal<T> {
}
}
#[derive(Copy, Clone, Debug)]
pub enum OffsetAlignment {
Start,
End,
Center,
Anchor,
}
impl OffsetAlignment {
pub fn align(&self, start: f32, end: f32) -> f32 {
match self {
OffsetAlignment::Start => start,
OffsetAlignment::End => end,
OffsetAlignment::Center => (start + end) / 2.0,
OffsetAlignment::Anchor => 0.0,
}
}
}
pub struct Offset<T> {
inner: T,
offset: Vec2,
@ -96,7 +115,7 @@ pub struct Offset<T> {
impl_shell_inner!(Offset);
impl<T: Widget> Offset<T> {
impl<T> Offset<T> {
pub fn new(inner: T, offset: Vec2) -> Self {
Self { inner, offset }
}
@ -106,6 +125,21 @@ impl<T: Widget> Offset<T> {
}
}
impl<T: RectBounds> Offset<T> {
pub fn new_aligned(
inner: T,
anchor: Vec2,
hori_align: OffsetAlignment,
vert_align: OffsetAlignment,
) -> Self {
let bounds = inner.get_bounds();
let x = hori_align.align(bounds.bl.x, bounds.tr.x);
let y = vert_align.align(bounds.tr.y, bounds.bl.y);
let offset = anchor - Vec2::new(x, y);
Self { inner, offset }
}
}
impl<T: Widget> Widget for Offset<T> {
fn update(&mut self, dt: f32) {
self.inner.update(dt);