mirror of
https://github.com/griffi-gh/hUI.git
synced 2024-12-22 04:18:21 -06:00
use rect om frame api
This commit is contained in:
parent
104ac018fe
commit
b30fe304d1
|
@ -375,7 +375,7 @@ impl UiElement for Container {
|
|||
// });
|
||||
// }
|
||||
|
||||
self.background_frame.draw(ctx.draw, ctx.layout.position, ctx.measure.size);
|
||||
self.background_frame.draw(ctx.draw, (ctx.layout.position, ctx.measure.size).into());
|
||||
|
||||
//padding
|
||||
position += vec2(self.padding.left, self.padding.top);
|
||||
|
|
|
@ -63,6 +63,6 @@ impl UiElement for FrameView {
|
|||
}
|
||||
|
||||
fn process(&self, ctx: ProcessContext) {
|
||||
self.frame.draw(ctx.draw, ctx.layout.position, ctx.measure.size);
|
||||
self.frame.draw(ctx.draw, (ctx.layout.position, ctx.measure.size).into());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -75,10 +75,10 @@ impl UiElement for ProgressBar {
|
|||
|
||||
//FIXME: these optimizations may not be valid
|
||||
if value < 1. || !self.foreground.covers_opaque() {
|
||||
self.background.draw(ctx.draw, ctx.layout.position, ctx.measure.size);
|
||||
self.background.draw(ctx.draw, (ctx.layout.position, ctx.measure.size).into());
|
||||
}
|
||||
if value > 0. {
|
||||
self.foreground.draw(ctx.draw, ctx.layout.position, ctx.measure.size * vec2(value, 1.));
|
||||
self.foreground.draw(ctx.draw, (ctx.layout.position, ctx.measure.size * vec2(value, 1.)).into());
|
||||
}
|
||||
|
||||
// let rounded_corners =
|
||||
|
|
|
@ -156,8 +156,10 @@ impl UiElement for Slider {
|
|||
if !(self.track_active.covers_opaque() && self.handle.covers_opaque() && (self.handle_size.1 >= self.track_height) && self.value >= 1.) {
|
||||
self.track.draw(
|
||||
ctx.draw,
|
||||
ctx.layout.position + ctx.measure.size * vec2(0., 0.5 - self.track_height / 2.),
|
||||
ctx.measure.size * vec2(1., self.track_height),
|
||||
(
|
||||
ctx.layout.position + ctx.measure.size * vec2(0., 0.5 - self.track_height / 2.),
|
||||
ctx.measure.size * vec2(1., self.track_height),
|
||||
).into()
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -168,8 +170,10 @@ impl UiElement for Slider {
|
|||
if !(self.handle.covers_opaque() && (self.handle_size.1 >= self.track_height) && self.value <= 0.) {
|
||||
self.track_active.draw(
|
||||
ctx.draw,
|
||||
ctx.layout.position + ctx.measure.size * vec2(0., 0.5 - self.track_height / 2.),
|
||||
(ctx.measure.size - handle_size * Vec2::X) * vec2(self.value, self.track_height) + handle_size * Vec2::X / 2.,
|
||||
(
|
||||
ctx.layout.position + ctx.measure.size * vec2(0., 0.5 - self.track_height / 2.),
|
||||
(ctx.measure.size - handle_size * Vec2::X) * vec2(self.value, self.track_height) + handle_size * Vec2::X / 2.,
|
||||
).into()
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -187,10 +191,12 @@ impl UiElement for Slider {
|
|||
if (self.handle_size.0 > 0. && self.handle_size.1 > 0.) {
|
||||
self.handle.draw(
|
||||
ctx.draw,
|
||||
ctx.layout.position +
|
||||
((ctx.measure.size.x - handle_size.x) * self.value) * Vec2::X +
|
||||
ctx.measure.size.y * ((1. - self.handle_size.1) * 0.5) * Vec2::Y,
|
||||
handle_size,
|
||||
(
|
||||
ctx.layout.position +
|
||||
((ctx.measure.size.x - handle_size.x) * self.value) * Vec2::X +
|
||||
ctx.measure.size.y * ((1. - self.handle_size.1) * 0.5) * Vec2::Y,
|
||||
handle_size,
|
||||
).into()
|
||||
);
|
||||
}
|
||||
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
//! modular procedural background system
|
||||
|
||||
use glam::Vec2;
|
||||
use crate::draw::UiDrawCommandList;
|
||||
use crate::{draw::UiDrawCommandList, rect::Rect};
|
||||
|
||||
pub mod point;
|
||||
mod rect;
|
||||
|
@ -13,8 +12,8 @@ pub use rect::RectFrame;
|
|||
|
||||
/// Trait for a drawable frame
|
||||
pub trait Frame {
|
||||
/// Draw the frame at the given position and size
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2);
|
||||
/// Draw the frame at the given rect's position and size
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect);
|
||||
|
||||
/// Check if the frame is guaranteed to be fully opaque and fully cover the parent frame regardless of it's size
|
||||
///
|
||||
|
|
|
@ -3,14 +3,14 @@ use super::Frame;
|
|||
use crate::{
|
||||
color,
|
||||
draw::{ImageHandle, UiDrawCommand, UiDrawCommandList},
|
||||
rect::{Corners, FillColor},
|
||||
rect::{Rect, Corners, FillColor},
|
||||
};
|
||||
|
||||
impl Frame for ImageHandle {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
draw.add(UiDrawCommand::Rectangle {
|
||||
position,
|
||||
size: parent_size,
|
||||
position: rect.position,
|
||||
size: rect.size,
|
||||
color: color::WHITE.into(),
|
||||
texture: Some(*self),
|
||||
texture_uv: None,
|
||||
|
@ -24,10 +24,10 @@ impl Frame for ImageHandle {
|
|||
}
|
||||
|
||||
impl Frame for FillColor {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
draw.add(UiDrawCommand::Rectangle {
|
||||
position,
|
||||
size: parent_size,
|
||||
position: rect.position,
|
||||
size: rect.size,
|
||||
color: self.corners(),
|
||||
texture: None,
|
||||
texture_uv: None,
|
||||
|
@ -45,8 +45,8 @@ impl Frame for FillColor {
|
|||
// Corners (RGBA):
|
||||
|
||||
impl Frame for Corners<Vec4> {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -54,8 +54,8 @@ impl Frame for Corners<Vec4> {
|
|||
}
|
||||
|
||||
impl Frame for (Vec4, Vec4, Vec4, Vec4) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -63,8 +63,8 @@ impl Frame for (Vec4, Vec4, Vec4, Vec4) {
|
|||
}
|
||||
|
||||
impl Frame for ((f32, f32, f32, f32), (f32, f32, f32, f32), (f32, f32, f32, f32), (f32, f32, f32, f32)) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -72,8 +72,8 @@ impl Frame for ((f32, f32, f32, f32), (f32, f32, f32, f32), (f32, f32, f32, f32)
|
|||
}
|
||||
|
||||
impl Frame for [[f32; 4]; 4] {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -83,8 +83,8 @@ impl Frame for [[f32; 4]; 4] {
|
|||
// Corners (RGB):
|
||||
|
||||
impl Frame for Corners<Vec3> {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -92,8 +92,8 @@ impl Frame for Corners<Vec3> {
|
|||
}
|
||||
|
||||
impl Frame for (Vec3, Vec3, Vec3, Vec3) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -101,8 +101,8 @@ impl Frame for (Vec3, Vec3, Vec3, Vec3) {
|
|||
}
|
||||
|
||||
impl Frame for ((f32, f32, f32), (f32, f32, f32), (f32, f32, f32), (f32, f32, f32)) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -110,8 +110,8 @@ impl Frame for ((f32, f32, f32), (f32, f32, f32), (f32, f32, f32), (f32, f32, f3
|
|||
}
|
||||
|
||||
impl Frame for [[f32; 3]; 4] {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -121,8 +121,8 @@ impl Frame for [[f32; 3]; 4] {
|
|||
// RGBA:
|
||||
|
||||
impl Frame for Vec4 {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -130,8 +130,8 @@ impl Frame for Vec4 {
|
|||
}
|
||||
|
||||
impl Frame for (f32, f32, f32, f32) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -139,8 +139,8 @@ impl Frame for (f32, f32, f32, f32) {
|
|||
}
|
||||
|
||||
impl Frame for [f32; 4] {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -150,8 +150,8 @@ impl Frame for [f32; 4] {
|
|||
// RGB:
|
||||
|
||||
impl Frame for Vec3 {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -159,8 +159,8 @@ impl Frame for Vec3 {
|
|||
}
|
||||
|
||||
impl Frame for (f32, f32, f32) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
@ -168,8 +168,8 @@ impl Frame for (f32, f32, f32) {
|
|||
}
|
||||
|
||||
impl Frame for [f32; 3] {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
FillColor::from(*self).draw(draw, position, parent_size)
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
FillColor::from(*self).draw(draw, rect)
|
||||
}
|
||||
fn covers_opaque(&self) -> bool {
|
||||
FillColor::from(*self).is_opaque()
|
||||
|
|
|
@ -4,7 +4,11 @@
|
|||
//! This is useful for creating scalable UI elements like buttons, windows, etc.
|
||||
|
||||
use glam::{vec2, UVec2, Vec2};
|
||||
use crate::{color, draw::{ImageHandle, UiDrawCommand}, rect::{Corners, FillColor, Rect}};
|
||||
use crate::{
|
||||
color,
|
||||
draw::{ImageHandle, UiDrawCommand, UiDrawCommandList},
|
||||
rect::{Rect, Corners, FillColor}
|
||||
};
|
||||
use super::Frame;
|
||||
|
||||
/// Represents a 9-patch image asset
|
||||
|
@ -49,10 +53,10 @@ impl Default for NinePatchFrame {
|
|||
}
|
||||
|
||||
impl Frame for NinePatchFrame {
|
||||
fn draw(&self, draw: &mut crate::draw::UiDrawCommandList, position: glam::Vec2, parent_size: glam::Vec2) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
// without this, shїt gets messed up when the position is not a whole number
|
||||
//XXX: should we round the size as well?
|
||||
let position = position.round();
|
||||
let position = rect.position.round();
|
||||
|
||||
let img_sz = UVec2::from(self.asset.size).as_vec2();
|
||||
|
||||
|
@ -79,13 +83,13 @@ impl Frame for NinePatchFrame {
|
|||
|
||||
let size_h = (
|
||||
corners_image_px.top_left.x,
|
||||
parent_size.x - corners_image_px.top_left.x - (img_sz.x - corners_image_px.top_right.x),
|
||||
rect.size.x - corners_image_px.top_left.x - (img_sz.x - corners_image_px.top_right.x),
|
||||
img_sz.x - corners_image_px.top_right.x,
|
||||
);
|
||||
|
||||
let size_v = (
|
||||
corners_image_px.top_left.y,
|
||||
parent_size.y - corners_image_px.top_left.y - (img_sz.y - corners_image_px.bottom_left.y),
|
||||
rect.size.y - corners_image_px.top_left.y - (img_sz.y - corners_image_px.bottom_left.y),
|
||||
img_sz.y - corners_image_px.bottom_left.y,
|
||||
);
|
||||
|
||||
|
|
|
@ -2,7 +2,7 @@ use glam::Vec2;
|
|||
use crate::{
|
||||
color,
|
||||
draw::{ImageHandle, RoundedCorners, UiDrawCommand, UiDrawCommandList},
|
||||
rect::{Corners, FillColor},
|
||||
rect::{Rect, Corners, FillColor},
|
||||
};
|
||||
use super::{Frame, point::FramePoint2d};
|
||||
|
||||
|
@ -115,12 +115,12 @@ impl Default for RectFrame {
|
|||
}
|
||||
|
||||
impl Frame for RectFrame {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
//TODO: handle bottom_right < top_left
|
||||
let top_left = self.top_left.resolve(parent_size);
|
||||
let bottom_right = self.bottom_right.resolve(parent_size);
|
||||
let top_left = self.top_left.resolve(rect.size);
|
||||
let bottom_right = self.bottom_right.resolve(rect.size);
|
||||
draw.add(UiDrawCommand::Rectangle {
|
||||
position: position + top_left,
|
||||
position: rect.position + top_left,
|
||||
size: bottom_right - top_left,
|
||||
color: self.color.corners(),
|
||||
texture: self.image,
|
||||
|
|
|
@ -1,16 +1,15 @@
|
|||
//! allows stacking two frames on top of each other
|
||||
|
||||
use glam::Vec2;
|
||||
use crate::draw::UiDrawCommandList;
|
||||
use crate::{draw::UiDrawCommandList, rect::Rect};
|
||||
use super::Frame;
|
||||
|
||||
/// A frame that draws two frames on top of each other
|
||||
pub struct FrameStack(pub Box<dyn Frame>, pub Box<dyn Frame>);
|
||||
|
||||
impl Frame for FrameStack {
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, position: Vec2, parent_size: Vec2) {
|
||||
self.0.draw(draw, position, parent_size);
|
||||
self.1.draw(draw, position, parent_size);
|
||||
fn draw(&self, draw: &mut UiDrawCommandList, rect: Rect) {
|
||||
self.0.draw(draw, rect);
|
||||
self.1.draw(draw, rect);
|
||||
}
|
||||
|
||||
fn covers_opaque(&self) -> bool {
|
||||
|
@ -22,10 +21,17 @@ impl Frame for FrameStack {
|
|||
pub trait FrameStackExt: Frame {
|
||||
/// Stack another frame on top of this one
|
||||
fn stack(self, other: impl Frame + 'static) -> FrameStack;
|
||||
|
||||
/// Stack another frame below this one
|
||||
fn stack_bottom(self, other: impl Frame + 'static) -> FrameStack;
|
||||
}
|
||||
|
||||
impl<T: Frame + 'static> FrameStackExt for T {
|
||||
fn stack(self, other: impl Frame + 'static) -> FrameStack {
|
||||
FrameStack(Box::new(self), Box::new(other))
|
||||
}
|
||||
|
||||
fn stack_bottom(self, other: impl Frame + 'static) -> FrameStack {
|
||||
FrameStack(Box::new(other), Box::new(self))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -88,3 +88,51 @@ impl From<Vec2> for Rect {
|
|||
Self::from_size(size)
|
||||
}
|
||||
}
|
||||
|
||||
impl From<(Vec2, Vec2)> for Rect {
|
||||
/// Create a new `Rect` from a tuple of two `Vec2`s, where the first `Vec2` is the position and the second `Vec2` is the size.
|
||||
fn from((position, size): (Vec2, Vec2)) -> Self {
|
||||
Self { position, size }
|
||||
}
|
||||
}
|
||||
|
||||
impl From<(f32, f32, f32, f32)> for Rect {
|
||||
/// Create a new `Rect` from a tuple of 4 `f32`s, where the first two `f32`s are the x and y positions of the top-left corner and the last two `f32`s are the width and height of the rect respectively.
|
||||
fn from((x, y, width, height): (f32, f32, f32, f32)) -> Self {
|
||||
Self {
|
||||
position: Vec2::new(x, y),
|
||||
size: Vec2::new(width, height),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<[f32; 4]> for Rect {
|
||||
/// Create a new `Rect` from an array of 4 `f32`s, where the first two `f32`s are the x and y positions of the top-left corner and the last two `f32`s are the width and height of the rect respectively.
|
||||
fn from([x, y, width, height]: [f32; 4]) -> Self {
|
||||
Self {
|
||||
position: Vec2::new(x, y),
|
||||
size: Vec2::new(width, height),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<Rect> for (Vec2, Vec2) {
|
||||
/// Convert a `Rect` into a tuple of two `Vec2`s, where the first `Vec2` is the position and the second `Vec2` is the size.
|
||||
fn from(rect: Rect) -> Self {
|
||||
(rect.position, rect.size)
|
||||
}
|
||||
}
|
||||
|
||||
impl From<Rect> for (f32, f32, f32, f32) {
|
||||
/// Convert a `Rect` into a tuple of 4 `f32`s, where the first two `f32`s are the x and y positions of the top-left corner and the last two `f32`s are the width and height of the rect respectively.
|
||||
fn from(rect: Rect) -> Self {
|
||||
(rect.position.x, rect.position.y, rect.size.x, rect.size.y)
|
||||
}
|
||||
}
|
||||
|
||||
impl From<Rect> for [f32; 4] {
|
||||
/// Convert a `Rect` into an array of 4 `f32`s, where the first two `f32`s are the x and y positions of the top-left corner and the last two `f32`s are the width and height of the rect respectively.
|
||||
fn from(rect: Rect) -> Self {
|
||||
[rect.position.x, rect.position.y, rect.size.x, rect.size.y]
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue