Winio is a single-threaded asynchronous GUI runtime.
It is based on compio, and the GUI part is powered by Win32, WinUI 3, Qt 5/6, GTK 4 or AppKit.
All IO requests could be issued in the same thread as GUI, without blocking the user interface!
Read the examples and learn more!
| Backend | Light | Dark |
|---|---|---|
| Win32 | ![]() |
![]() |
| WinUI 3 | ![]() |
![]() |
| Qt 6 | ![]() |
![]() |
| GTK 4 | ![]() |
![]() |
| AppKit | ![]() |
![]() |
Winio follows ELM-like design, inspired by yew and relm4.
The application starts with a root Component:
use winio::prelude::*;
fn main() -> Result<()> {
App::new("rs.compio.winio.example")?.run::<MainModel>(())
}
struct MainModel {
window: Child<Window>,
}
enum MainMessage {
Noop,
Close,
}
impl Component for MainModel {
type Error = Error;
type Event = ();
type Init<'a> = ();
type Message = MainMessage;
async fn init(_init: Self::Init<'_>, _sender: &ComponentSender<Self>) -> Result<Self> {
// create & initialize the window
init! {
window: Window = (()) => {
text: "Example",
size: Size::new(800.0, 600.0),
}
}
window.show()?;
Ok(Self { window })
}
async fn start(&mut self, sender: &ComponentSender<Self>) -> ! {
// listen to events
start! {
sender, default: MainMessage::Noop,
self.window => {
WindowEvent::Close => MainMessage::Close,
}
}
}
async fn update_children(&mut self) -> Result<bool> {
// update the window
update_children!(self.window)
}
async fn update(&mut self, message: Self::Message, sender: &ComponentSender<Self>) -> Result<bool> {
// deal with custom messages
match message {
MainMessage::Noop => Ok(false),
MainMessage::Close => {
// the root component output stops the application
sender.output(());
// need not to call `render`
Ok(false)
}
}
}
fn render(&mut self, _sender: &ComponentSender<Self>) -> Result<()> {
let csize = self.window.client_size()?;
// adjust layout and draw widgets here
Ok(())
}
fn render_children(&mut self) -> Result<()> {
self.window.render()
}
}








