This commit is contained in:
2025-07-28 00:01:12 +02:00
parent cba301db74
commit d9c23f1f09
5 changed files with 99 additions and 18 deletions
+38 -3
View File
@@ -1,19 +1,19 @@
use std::sync::Arc; use std::sync::Arc;
use crate::{widget::Element}; use crate::widget::Element;
pub trait DependencyHandler: std::fmt::Debug + Send + Sync { pub trait DependencyHandler: std::fmt::Debug + Send + Sync {
fn add(&self); fn add(&self);
fn check(&self) -> bool; fn check(&self) -> bool;
} }
pub struct Dependency<T: Element> { pub struct Dependency<T> {
handlers: Vec<std::sync::Arc<dyn DependencyHandler>>, handlers: Vec<std::sync::Arc<dyn DependencyHandler>>,
element: T, element: T,
element_reset: Box<dyn FnMut() -> T + Send + Sync>, element_reset: Box<dyn FnMut() -> T + Send + Sync>,
} }
impl<T: Element> Dependency<T> { impl<T> Dependency<T> {
pub fn new<F: FnMut() -> T + Send + Sync + 'static>(mut f: F) -> Self { pub fn new<F: FnMut() -> T + Send + Sync + 'static>(mut f: F) -> Self {
Self { Self {
handlers: Vec::new(), handlers: Vec::new(),
@@ -22,6 +22,21 @@ impl<T: Element> Dependency<T> {
} }
} }
pub fn from(
mut f: Box<dyn FnMut() -> T + Send + Sync>,
handlers: Vec<std::sync::Arc<dyn DependencyHandler>>,
) -> Self {
for h in &handlers {
h.add();
}
Self {
handlers,
element: f(),
element_reset: f,
}
}
pub fn auto_reset(&mut self) { pub fn auto_reset(&mut self) {
for i in &self.handlers { for i in &self.handlers {
if i.check() { if i.check() {
@@ -37,6 +52,26 @@ impl<T: Element> Dependency<T> {
} }
} }
impl Element for Dependency<Box<dyn Element>> {
fn render(&mut self, scope: &mut crate::render_scope::RenderScope) {
self.element.render(scope);
self.auto_reset();
}
fn after_render(&mut self, scope: &crate::render_scope::RenderScope) {
self.element.after_render(scope);
self.auto_reset();
}
fn as_any(&self) -> &dyn std::any::Any {
self
}
fn as_any_mut(&mut self) -> &mut dyn std::any::Any {
self
}
}
impl<T: Element + 'static> Element for Dependency<T> { impl<T: Element + 'static> Element for Dependency<T> {
fn render(&mut self, scope: &mut crate::render_scope::RenderScope) { fn render(&mut self, scope: &mut crate::render_scope::RenderScope) {
self.element.render(scope); self.element.render(scope);
+23
View File
@@ -0,0 +1,23 @@
use std::sync::Arc;
use crate::{
dependency::{Dependency, DependencyHandler},
widget::{Element, Widget},
Screen,
};
pub struct Rsx(
pub Vec<(
Box<dyn FnMut() -> Box<dyn Element> + Send + Sync>,
Vec<std::sync::Arc<dyn DependencyHandler>>,
)>,
);
impl Rsx {
pub fn draw(self, screen: &Arc<Screen>) {
for i in self.0 {
let d = Dependency::from(i.0, i.1);
screen.draw_widget(Widget::new(Box::new(d)));
}
}
}
+7
View File
@@ -10,6 +10,7 @@ use crate::{
pub mod dependency; pub mod dependency;
pub mod elements; pub mod elements;
pub mod extensions; pub mod extensions;
pub mod frontend;
pub mod macros; pub mod macros;
pub mod render_scope; pub mod render_scope;
pub mod style; pub mod style;
@@ -46,6 +47,12 @@ impl Screen {
w w
} }
pub fn draw_widget(self: &Arc<Self>, w: Widget) -> Arc<Widget> {
let w = Arc::new(w);
self.widgets.lock().unwrap().push(w.clone());
w
}
pub fn extension<E: Extension + Send + Sync + 'static>(self: &Arc<Self>, ext: E) { pub fn extension<E: Extension + Send + Sync + 'static>(self: &Arc<Self>, ext: E) {
self.extensions self.extensions
.lock() .lock()
+16 -1
View File
@@ -125,5 +125,20 @@ macro_rules! event_handler {
#[macro_export] #[macro_export]
macro_rules! rsx { macro_rules! rsx {
() => {}; ($($inner:tt)*) => {{
let mut r = Rsx(Vec::new());
$crate::rsx_inner! { r, $($inner)* };
r
}};
}
#[macro_export]
macro_rules! rsx_inner {
($r:expr, $(%$dep:ident)* $s:literal $($rest:tt)*) => {
$r.0.push((Box::new({ $(let $dep = $dep.clone();)* move || Box::new(format!($s)) }), vec![$(Arc::new($dep.clone()),)*]));
$crate::rsx_inner!{ $r, $($rest)* };
};
($r:expr,) => {};
} }
+15 -14
View File
@@ -1,26 +1,27 @@
use osui::{dependency::Dependency, elements::state::use_state, style::Transform, Screen}; use std::sync::Arc;
use osui::{elements::state::use_state, frontend::Rsx, rsx, Screen};
fn main() -> std::io::Result<()> { fn main() -> std::io::Result<()> {
let screen = Screen::new(); let screen = Screen::new();
app().draw(&screen);
screen.run()
}
fn app() -> Rsx {
let count = use_state(0); let count = use_state(0);
std::thread::spawn({ std::thread::spawn({
let count = count.clone(); let count = count.clone();
move || loop { move || loop {
std::thread::sleep(std::time::Duration::from_millis(1000)); std::thread::sleep(std::time::Duration::from_millis(50));
**count.get() += 500; **count.get() += 1;
} }
}); });
screen rsx! {
.draw( %count "{count}"
Dependency::new({ }
let count = count.clone();
move || format!("{count}")
})
.add(count.clone()),
)
.component(Transform::center());
screen.run()
} }