constify and deinline some methods

This commit is contained in:
🪞👃🪞 2025-04-13 21:11:07 +03:00
parent 4279503681
commit 18a01b8355
10 changed files with 124 additions and 92 deletions

View file

@ -6,77 +6,75 @@ pub trait Area<N: Coordinate>: From<[N;4]> + Debug + Copy {
fn y (&self) -> N;
fn w (&self) -> N;
fn h (&self) -> N;
#[inline] fn zero () -> [N;4] {
fn zero () -> [N;4] {
[N::zero(), N::zero(), N::zero(), N::zero()]
}
#[inline] fn from_position (pos: impl Size<N>) -> [N;4] {
fn from_position (pos: impl Size<N>) -> [N;4] {
let [x, y] = pos.wh();
[x, y, 0.into(), 0.into()]
}
#[inline] fn from_size (size: impl Size<N>) -> [N;4] {
fn from_size (size: impl Size<N>) -> [N;4] {
let [w, h] = size.wh();
[0.into(), 0.into(), w, h]
}
#[inline] fn expect_min (&self, w: N, h: N) -> Usually<&Self> {
fn expect_min (&self, w: N, h: N) -> Usually<&Self> {
if self.w() < w || self.h() < h {
Err(format!("min {w}x{h}").into())
} else {
Ok(self)
}
}
#[inline] fn xy (&self) -> [N;2] {
fn xy (&self) -> [N;2] {
[self.x(), self.y()]
}
#[inline] fn wh (&self) -> [N;2] {
fn wh (&self) -> [N;2] {
[self.w(), self.h()]
}
#[inline] fn xywh (&self) -> [N;4] {
fn xywh (&self) -> [N;4] {
[self.x(), self.y(), self.w(), self.h()]
}
#[inline] fn clip_h (&self, h: N) -> [N;4] {
fn clip_h (&self, h: N) -> [N;4] {
[self.x(), self.y(), self.w(), self.h().min(h)]
}
#[inline] fn clip_w (&self, w: N) -> [N;4] {
fn clip_w (&self, w: N) -> [N;4] {
[self.x(), self.y(), self.w().min(w), self.h()]
}
#[inline] fn clip (&self, wh: impl Size<N>) -> [N;4] {
fn clip (&self, wh: impl Size<N>) -> [N;4] {
[self.x(), self.y(), wh.w(), wh.h()]
}
#[inline] fn set_w (&self, w: N) -> [N;4] {
fn set_w (&self, w: N) -> [N;4] {
[self.x(), self.y(), w, self.h()]
}
#[inline] fn set_h (&self, h: N) -> [N;4] {
fn set_h (&self, h: N) -> [N;4] {
[self.x(), self.y(), self.w(), h]
}
#[inline] fn x2 (&self) -> N {
fn x2 (&self) -> N {
self.x().plus(self.w())
}
#[inline] fn y2 (&self) -> N {
fn y2 (&self) -> N {
self.y().plus(self.h())
}
#[inline] fn lrtb (&self) -> [N;4] {
fn lrtb (&self) -> [N;4] {
[self.x(), self.x2(), self.y(), self.y2()]
}
#[inline] fn center (&self) -> [N;2] {
fn center (&self) -> [N;2] {
[self.x().plus(self.w()/2.into()), self.y().plus(self.h()/2.into())]
}
#[inline] fn center_x (&self, n: N) -> [N;4] {
fn center_x (&self, n: N) -> [N;4] {
let [x, y, w, h] = self.xywh();
[(x.plus(w / 2.into())).minus(n / 2.into()), y.plus(h / 2.into()), n, 1.into()]
}
#[inline] fn center_y (&self, n: N) -> [N;4] {
fn center_y (&self, n: N) -> [N;4] {
let [x, y, w, h] = self.xywh();
[x.plus(w / 2.into()), (y.plus(h / 2.into())).minus(n / 2.into()), 1.into(), n]
}
#[inline] fn center_xy (&self, [n, m]: [N;2]) -> [N;4] {
fn center_xy (&self, [n, m]: [N;2]) -> [N;4] {
let [x, y, w, h] = self.xywh();
[(x.plus(w / 2.into())).minus(n / 2.into()), (y.plus(h / 2.into())).minus(m / 2.into()), n, m]
}
#[inline] fn centered (&self) -> [N;2] {
fn centered (&self) -> [N;2] {
[self.x().minus(self.w()/2.into()), self.y().minus(self.h()/2.into())]
}
fn iter_x (&self) -> impl Iterator<Item = N> where N: std::iter::Step {
self.x()..(self.x()+self.w())
}
@ -86,17 +84,17 @@ pub trait Area<N: Coordinate>: From<[N;4]> + Debug + Copy {
}
impl<N: Coordinate> Area<N> for (N, N, N, N) {
#[inline] fn x (&self) -> N { self.0 }
#[inline] fn y (&self) -> N { self.1 }
#[inline] fn w (&self) -> N { self.2 }
#[inline] fn h (&self) -> N { self.3 }
fn x (&self) -> N { self.0 }
fn y (&self) -> N { self.1 }
fn w (&self) -> N { self.2 }
fn h (&self) -> N { self.3 }
}
impl<N: Coordinate> Area<N> for [N;4] {
#[inline] fn x (&self) -> N { self[0] }
#[inline] fn y (&self) -> N { self[1] }
#[inline] fn w (&self) -> N { self[2] }
#[inline] fn h (&self) -> N { self[3] }
fn x (&self) -> N { self[0] }
fn y (&self) -> N { self[1] }
fn w (&self) -> N { self[2] }
fn h (&self) -> N { self[3] }
}
#[cfg(test)] mod test_area {

View file

@ -1,12 +1,6 @@
use std::fmt::{Debug, Display};
use std::ops::{Add, Sub, Mul, Div};
impl Coordinate for u16 {
#[inline] fn plus (self, other: Self) -> Self {
self.saturating_add(other)
}
}
/// A linear coordinate.
pub trait Coordinate: Send + Sync + Copy
+ Add<Self, Output=Self>
@ -19,13 +13,19 @@ pub trait Coordinate: Send + Sync + Copy
+ Into<usize>
+ Into<f64>
{
#[inline] fn zero () -> Self { 0.into() }
#[inline] fn minus (self, other: Self) -> Self {
fn zero () -> Self { 0.into() }
fn plus (self, other: Self) -> Self;
fn minus (self, other: Self) -> Self {
if self >= other {
self - other
} else {
0.into()
}
}
fn plus (self, other: Self) -> Self;
}
impl Coordinate for u16 {
fn plus (self, other: Self) -> Self {
self.saturating_add(other)
}
}

View file

@ -63,17 +63,17 @@ try_from_expr!(<'a, E>: Align<RenderBox<'a, E>>: |state, iter|{
});
impl<A> Align<A> {
#[inline] pub fn c (a: A) -> Self { Self(Alignment::Center, a) }
#[inline] pub fn x (a: A) -> Self { Self(Alignment::X, a) }
#[inline] pub fn y (a: A) -> Self { Self(Alignment::Y, a) }
#[inline] pub fn n (a: A) -> Self { Self(Alignment::N, a) }
#[inline] pub fn s (a: A) -> Self { Self(Alignment::S, a) }
#[inline] pub fn e (a: A) -> Self { Self(Alignment::E, a) }
#[inline] pub fn w (a: A) -> Self { Self(Alignment::W, a) }
#[inline] pub fn nw (a: A) -> Self { Self(Alignment::NW, a) }
#[inline] pub fn sw (a: A) -> Self { Self(Alignment::SW, a) }
#[inline] pub fn ne (a: A) -> Self { Self(Alignment::NE, a) }
#[inline] pub fn se (a: A) -> Self { Self(Alignment::SE, a) }
#[inline] pub const fn c (a: A) -> Self { Self(Alignment::Center, a) }
#[inline] pub const fn x (a: A) -> Self { Self(Alignment::X, a) }
#[inline] pub const fn y (a: A) -> Self { Self(Alignment::Y, a) }
#[inline] pub const fn n (a: A) -> Self { Self(Alignment::N, a) }
#[inline] pub const fn s (a: A) -> Self { Self(Alignment::S, a) }
#[inline] pub const fn e (a: A) -> Self { Self(Alignment::E, a) }
#[inline] pub const fn w (a: A) -> Self { Self(Alignment::W, a) }
#[inline] pub const fn nw (a: A) -> Self { Self(Alignment::NW, a) }
#[inline] pub const fn sw (a: A) -> Self { Self(Alignment::SW, a) }
#[inline] pub const fn ne (a: A) -> Self { Self(Alignment::NE, a) }
#[inline] pub const fn se (a: A) -> Self { Self(Alignment::SE, a) }
}
impl<E: Output, A: Content<E>> Content<E> for Align<A> {
fn content (&self) -> impl Render<E> {

View file

@ -41,12 +41,12 @@ try_from_expr!(<'a, E>: Bsp<RenderBox<'a, E>, RenderBox<'a, E>>: |state, iter| {
}
});
impl<A, B> Bsp<A, B> {
#[inline] pub fn n (a: A, b: B) -> Self { Self(North, a, b) }
#[inline] pub fn s (a: A, b: B) -> Self { Self(South, a, b) }
#[inline] pub fn e (a: A, b: B) -> Self { Self(East, a, b) }
#[inline] pub fn w (a: A, b: B) -> Self { Self(West, a, b) }
#[inline] pub fn a (a: A, b: B) -> Self { Self(Above, a, b) }
#[inline] pub fn b (a: A, b: B) -> Self { Self(Below, a, b) }
#[inline] pub const fn n (a: A, b: B) -> Self { Self(North, a, b) }
#[inline] pub const fn s (a: A, b: B) -> Self { Self(South, a, b) }
#[inline] pub const fn e (a: A, b: B) -> Self { Self(East, a, b) }
#[inline] pub const fn w (a: A, b: B) -> Self { Self(West, a, b) }
#[inline] pub const fn a (a: A, b: B) -> Self { Self(Above, a, b) }
#[inline] pub const fn b (a: A, b: B) -> Self { Self(Below, a, b) }
}
pub trait BspAreas<E: Output, A: Content<E>, B: Content<E>> {
fn direction (&self) -> Direction;

View file

@ -2,11 +2,21 @@ use crate::*;
/// Show an item only when a condition is true.
pub struct When<A>(pub bool, pub A);
impl<A> When<A> { #[inline] pub fn new (c: bool, a: A) -> Self { Self(c, a) } }
impl<A> When<A> {
/// Create a binary condition.
pub const fn new (c: bool, a: A) -> Self {
Self(c, a)
}
}
/// Show one item if a condition is true and another if the condition is false
pub struct Either<A, B>(pub bool, pub A, pub B);
impl<A, B> Either<A, B> { #[inline] pub fn new (c: bool, a: A, b: B) -> Self { Self(c, a, b) } }
impl<A, B> Either<A, B> {
/// Create a ternary condition.
pub const fn new (c: bool, a: A, b: B) -> Self {
Self(c, a, b)
}
}
#[cfg(feature = "dsl")]
try_from_expr!(<'a, E>: When<RenderBox<'a, E>>: |state, iter| {

View file

@ -40,9 +40,9 @@ impl<'a, E, A, B, I, F, G> Map<E, A, B, I, F, G> where
I: Iterator<Item = A> + Send + Sync + 'a,
F: Fn() -> I + Send + Sync + 'a,
{
pub fn new (get_iterator: F, get_item: G) -> Self {
pub const fn new (get_iterator: F, get_item: G) -> Self {
Self {
__: Default::default(),
__: PhantomData,
get_iterator,
get_item
}

View file

@ -12,7 +12,7 @@ impl<A, B, I, F, G> Reduce<A, B, I, F, G> where
F: Fn() -> I + Send + Sync,
G: Fn(A, B, usize)->A + Send + Sync
{
pub fn new (f: F, g: G) -> Self { Self(Default::default(), f, g) }
pub const fn new (f: F, g: G) -> Self { Self(Default::default(), f, g) }
}
impl<E: Output, A, B, I, F, G> Content<E> for Reduce<A, B, I, F, G> where

View file

@ -26,9 +26,9 @@ macro_rules! transform_xy {
($x:literal $y:literal $xy:literal |$self:ident : $Enum:ident, $to:ident|$area:expr) => {
pub enum $Enum<T> { X(T), Y(T), XY(T) }
impl<T> $Enum<T> {
#[inline] pub fn x (item: T) -> Self { Self::X(item) }
#[inline] pub fn y (item: T) -> Self { Self::Y(item) }
#[inline] pub fn xy (item: T) -> Self { Self::XY(item) }
#[inline] pub const fn x (item: T) -> Self { Self::X(item) }
#[inline] pub const fn y (item: T) -> Self { Self::Y(item) }
#[inline] pub const fn xy (item: T) -> Self { Self::XY(item) }
}
#[cfg(feature = "dsl")]
impl<'a, E: Output + 'a, T: ViewContext<'a, E>> TryFromAtom<'a, T>
@ -78,9 +78,9 @@ macro_rules! transform_xy_unit {
($x:literal $y:literal $xy:literal |$self:ident : $Enum:ident, $to:ident|$layout:expr) => {
pub enum $Enum<U, T> { X(U, T), Y(U, T), XY(U, U, T), }
impl<U, T> $Enum<U, T> {
#[inline] pub fn x (x: U, item: T) -> Self { Self::X(x, item) }
#[inline] pub fn y (y: U, item: T) -> Self { Self::Y(y, item) }
#[inline] pub fn xy (x: U, y: U, item: T) -> Self { Self::XY(x, y, item) }
#[inline] pub const fn x (x: U, item: T) -> Self { Self::X(x, item) }
#[inline] pub const fn y (y: U, item: T) -> Self { Self::Y(y, item) }
#[inline] pub const fn xy (x: U, y: U, item: T) -> Self { Self::XY(x, y, item) }
}
#[cfg(feature = "dsl")]
impl<'a, E: Output + 'a, T: ViewContext<'a, E>> TryFromAtom<'a, T>

View file

@ -4,39 +4,39 @@ use std::fmt::Debug;
pub trait Size<N: Coordinate>: From<[N;2]> + Debug + Copy {
fn x (&self) -> N;
fn y (&self) -> N;
#[inline] fn w (&self) -> N { self.x() }
#[inline] fn h (&self) -> N { self.y() }
#[inline] fn wh (&self) -> [N;2] { [self.x(), self.y()] }
#[inline] fn clip_w (&self, w: N) -> [N;2] { [self.w().min(w), self.h()] }
#[inline] fn clip_h (&self, h: N) -> [N;2] { [self.w(), self.h().min(h)] }
#[inline] fn expect_min (&self, w: N, h: N) -> Usually<&Self> {
fn w (&self) -> N { self.x() }
fn h (&self) -> N { self.y() }
fn wh (&self) -> [N;2] { [self.x(), self.y()] }
fn clip_w (&self, w: N) -> [N;2] { [self.w().min(w), self.h()] }
fn clip_h (&self, h: N) -> [N;2] { [self.w(), self.h().min(h)] }
fn expect_min (&self, w: N, h: N) -> Usually<&Self> {
if self.w() < w || self.h() < h {
Err(format!("min {w}x{h}").into())
} else {
Ok(self)
}
}
#[inline] fn zero () -> [N;2] {
fn zero () -> [N;2] {
[N::zero(), N::zero()]
}
#[inline] fn to_area_pos (&self) -> [N;4] {
fn to_area_pos (&self) -> [N;4] {
let [x, y] = self.wh();
[x, y, 0.into(), 0.into()]
}
#[inline] fn to_area_size (&self) -> [N;4] {
fn to_area_size (&self) -> [N;4] {
let [w, h] = self.wh();
[0.into(), 0.into(), w, h]
}
}
impl<N: Coordinate> Size<N> for (N, N) {
#[inline] fn x (&self) -> N { self.0 }
#[inline] fn y (&self) -> N { self.1 }
fn x (&self) -> N { self.0 }
fn y (&self) -> N { self.1 }
}
impl<N: Coordinate> Size<N> for [N;2] {
#[inline] fn x (&self) -> N { self[0] }
#[inline] fn y (&self) -> N { self[1] }
fn x (&self) -> N { self[0] }
fn y (&self) -> N { self[1] }
}
#[cfg(test)] mod test_size {

View file

@ -2,28 +2,39 @@ use crate::*;
use std::marker::PhantomData;
/// Lazily-evaluated [Render]able.
pub struct Thunk<E: Output, T: Render<E>, F: Fn()->T + Send + Sync>(PhantomData<E>, F);
pub struct Thunk<E: Output, T: Render<E>, F: Fn()->T + Send + Sync>(
PhantomData<E>,
F
);
impl<E: Output, T: Render<E>, F: Fn()->T + Send + Sync> Thunk<E, T, F> {
pub fn new (thunk: F) -> Self {
Self(Default::default(), thunk)
pub const fn new (thunk: F) -> Self {
Self(PhantomData, thunk)
}
}
impl<E: Output, T: Render<E>, F: Fn()->T + Send + Sync> Content<E> for Thunk<E, T, F> {
fn content (&self) -> impl Render<E> { (self.1)() }
}
pub struct ThunkBox<'a, E: Output>(PhantomData<E>, Box<dyn Fn()->RenderBox<'a, E> + Send + Sync + 'a>);
pub struct ThunkBox<'a, E: Output>(
PhantomData<E>,
Box<dyn Fn()->RenderBox<'a, E> + Send + Sync + 'a>
);
impl<'a, E: Output> ThunkBox<'a, E> {
pub fn new (thunk: Box<dyn Fn()->RenderBox<'a, E> + Send + Sync + 'a>) -> Self {
Self(Default::default(), thunk)
pub const fn new (thunk: Box<dyn Fn()->RenderBox<'a, E> + Send + Sync + 'a>) -> Self {
Self(PhantomData, thunk)
}
}
impl<'a, E: Output> Content<E> for ThunkBox<'a, E> {
fn content (&self) -> impl Render<E> { (self.1)() }
}
impl<'a, E: Output, F: Fn()->T + Send + Sync + 'a, T: Render<E> + Send + Sync + 'a> From<F> for ThunkBox<'a, E> {
impl<'a, E, F, T> From<F> for ThunkBox<'a, E>
where
E: Output,
F: Fn()->T + Send + Sync + 'a,
T: Render<E> + Send + Sync + 'a
{
fn from (f: F) -> Self {
Self(Default::default(), Box::new(move||f().boxed()))
Self(PhantomData, Box::new(move||f().boxed()))
}
}
//impl<'a, E: Output, F: Fn()->Box<dyn Render<E> + 'a> + Send + Sync + 'a> From<F> for ThunkBox<'a, E> {
@ -34,17 +45,30 @@ impl<'a, E: Output, F: Fn()->T + Send + Sync + 'a, T: Render<E> + Send + Sync +
pub struct ThunkRender<E: Output, F: Fn(&mut E) + Send + Sync>(PhantomData<E>, F);
impl<E: Output, F: Fn(&mut E) + Send + Sync> ThunkRender<E, F> {
pub fn new (render: F) -> Self { Self(Default::default(), render) }
pub fn new (render: F) -> Self { Self(PhantomData, render) }
}
impl<E: Output, F: Fn(&mut E) + Send + Sync> Content<E> for ThunkRender<E, F> {
fn render (&self, to: &mut E) { (self.1)(to) }
}
pub struct ThunkLayout<E: Output, F1: Fn(E::Area)->E::Area + Send + Sync, F2: Fn(&mut E) + Send + Sync>(PhantomData<E>, F1, F2);
pub struct ThunkLayout<
E: Output,
F1: Fn(E::Area)->E::Area + Send + Sync,
F2: Fn(&mut E) + Send + Sync
>(
PhantomData<E>,
F1,
F2
);
impl<E: Output, F1: Fn(E::Area)->E::Area + Send + Sync, F2: Fn(&mut E) + Send + Sync> ThunkLayout<E, F1, F2> {
pub fn new (layout: F1, render: F2) -> Self { Self(Default::default(), layout, render) }
pub fn new (layout: F1, render: F2) -> Self { Self(PhantomData, layout, render) }
}
impl<E: Output, F1: Fn(E::Area)->E::Area + Send + Sync, F2: Fn(&mut E) + Send + Sync> Content<E> for ThunkLayout<E, F1, F2> {
impl<E, F1, F2> Content<E> for ThunkLayout<E, F1, F2>
where
E: Output,
F1: Fn(E::Area)->E::Area + Send + Sync,
F2: Fn(&mut E) + Send + Sync
{
fn layout (&self, to: E::Area) -> E::Area { (self.1)(to) }
fn render (&self, to: &mut E) { (self.2)(to) }
}