Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Begin transition to a trait-based system #3386

Closed
wants to merge 8 commits into from
Closed
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ Unreleased` header.

# Unreleased

- **Breaking:** Removed unnecessary generic parameter `T` from `EventLoopWindowTarget`.
- On Windows, macOS, X11, Wayland and Web, implement setting images as cursors. See the `custom_cursors.rs` example.
- Add `Window::set_custom_cursor`
- Add `CustomCursor`
Expand Down
10 changes: 5 additions & 5 deletions examples/child_window.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,14 +16,14 @@ fn main() -> Result<(), impl std::error::Error> {
use winit::{
dpi::{LogicalPosition, LogicalSize, Position},
event::{ElementState, Event, KeyEvent, WindowEvent},
event_loop::{EventLoop, EventLoopWindowTarget},
event_loop::{ActiveEventLoop, EventLoop},
raw_window_handle::HasRawWindowHandle,
window::{Window, WindowBuilder, WindowId},
};

fn spawn_child_window(
parent: &Window,
event_loop: &EventLoopWindowTarget<()>,
event_loop: ActiveEventLoop<'_>,
windows: &mut HashMap<WindowId, Window>,
) {
let parent = parent.raw_window_handle().unwrap();
Expand Down Expand Up @@ -53,12 +53,12 @@ fn main() -> Result<(), impl std::error::Error> {

println!("parent window: {parent_window:?})");

event_loop.run(move |event: Event<()>, elwt| {
event_loop.run(move |event: Event<()>, event_loop| {
if let Event::WindowEvent { event, window_id } = event {
match event {
WindowEvent::CloseRequested => {
windows.clear();
elwt.exit();
event_loop.exit();
}
WindowEvent::CursorEntered { device_id: _ } => {
// On x11, println when the cursor entered in a window even if the child window is created
Expand All @@ -75,7 +75,7 @@ fn main() -> Result<(), impl std::error::Error> {
},
..
} => {
spawn_child_window(&parent_window, elwt, &mut windows);
spawn_child_window(&parent_window, event_loop, &mut windows);
}
WindowEvent::RedrawRequested => {
if let Some(window) = windows.get(&window_id) {
Expand Down
213 changes: 123 additions & 90 deletions examples/control_flow.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,11 @@ use web_time as time;

use simple_logger::SimpleLogger;
use winit::{
event::{ElementState, Event, KeyEvent, WindowEvent},
event_loop::{ControlFlow, EventLoop},
event::{ElementState, KeyEvent, WindowEvent},
event_loop::{ActiveEventLoop, ControlFlow, EventLoop},
handler::ApplicationHandler,
keyboard::{Key, NamedKey},
window::WindowBuilder,
window::{Window, WindowBuilder, WindowId},
};

#[path = "util/fill.rs"]
Expand All @@ -27,102 +28,134 @@ enum Mode {
const WAIT_TIME: time::Duration = time::Duration::from_millis(100);
const POLL_SLEEP_TIME: time::Duration = time::Duration::from_millis(100);

fn main() -> Result<(), impl std::error::Error> {
SimpleLogger::new().init().unwrap();

println!("Press '1' to switch to Wait mode.");
println!("Press '2' to switch to WaitUntil mode.");
println!("Press '3' to switch to Poll mode.");
println!("Press 'R' to toggle request_redraw() calls.");
println!("Press 'Esc' to close the window.");
struct App {
window: Window,
mode: Mode,
request_redraw: bool,
wait_cancelled: bool,
close_requested: bool,
}

let event_loop = EventLoop::new().unwrap();
let window = WindowBuilder::new()
.with_title("Press 1, 2, 3 to change control flow mode. Press R to toggle redraw requests.")
.build(&event_loop)
.unwrap();

let mut mode = Mode::Wait;
let mut request_redraw = false;
let mut wait_cancelled = false;
let mut close_requested = false;

event_loop.run(move |event, elwt| {
use winit::event::StartCause;
println!("{event:?}");
impl ApplicationHandler for App {
fn window_event(
&mut self,
_active: ActiveEventLoop<'_>,
_window_id: WindowId,
event: WindowEvent,
) {
match event {
Event::NewEvents(start_cause) => {
wait_cancelled = match start_cause {
StartCause::WaitCancelled { .. } => mode == Mode::WaitUntil,
_ => false,
}
WindowEvent::CloseRequested => {
self.close_requested = true;
}
Event::WindowEvent { event, .. } => match event {
WindowEvent::CloseRequested => {
close_requested = true;
WindowEvent::KeyboardInput {
event:
KeyEvent {
logical_key: key,
state: ElementState::Pressed,
..
},
..
} => match key.as_ref() {
// WARNING: Consider using `key_without_modifers()` if available on your platform.
// See the `key_binding` example
Key::Character("1") => {
self.mode = Mode::Wait;
println!("\nmode: {:?}\n", self.mode);
}
Key::Character("2") => {
self.mode = Mode::WaitUntil;
println!("\nmode: {:?}\n", self.mode);
}
Key::Character("3") => {
self.mode = Mode::Poll;
println!("\nmode: {:?}\n", self.mode);
}
WindowEvent::KeyboardInput {
event:
KeyEvent {
logical_key: key,
state: ElementState::Pressed,
..
},
..
} => match key.as_ref() {
// WARNING: Consider using `key_without_modifers()` if available on your platform.
// See the `key_binding` example
Key::Character("1") => {
mode = Mode::Wait;
println!("\nmode: {mode:?}\n");
}
Key::Character("2") => {
mode = Mode::WaitUntil;
println!("\nmode: {mode:?}\n");
}
Key::Character("3") => {
mode = Mode::Poll;
println!("\nmode: {mode:?}\n");
}
Key::Character("r") => {
request_redraw = !request_redraw;
println!("\nrequest_redraw: {request_redraw}\n");
}
Key::Named(NamedKey::Escape) => {
close_requested = true;
}
_ => (),
},
WindowEvent::RedrawRequested => {
fill::fill_window(&window);
Key::Character("r") => {
self.request_redraw = !self.request_redraw;
println!("\nrequest_redraw: {}\n", self.request_redraw);
}
Key::Named(NamedKey::Escape) => {
self.close_requested = true;
}
_ => (),
},
Event::AboutToWait => {
if request_redraw && !wait_cancelled && !close_requested {
window.request_redraw();
}
WindowEvent::RedrawRequested => {
fill::fill_window(&self.window);
}
_ => (),
}
}

fn start_wait_cancelled(
&mut self,
_active: ActiveEventLoop<'_>,
_start: time::Instant,
_requested_resume: Option<time::Instant>,
) {
self.wait_cancelled = self.mode == Mode::WaitUntil;
}

fn start_resume_time_reached(
&mut self,
_active: ActiveEventLoop<'_>,
_start: time::Instant,
_requested_resume: time::Instant,
) {
self.wait_cancelled = false;
}

match mode {
Mode::Wait => elwt.set_control_flow(ControlFlow::Wait),
Mode::WaitUntil => {
if !wait_cancelled {
elwt.set_control_flow(ControlFlow::WaitUntil(
time::Instant::now() + WAIT_TIME,
));
}
}
Mode::Poll => {
thread::sleep(POLL_SLEEP_TIME);
elwt.set_control_flow(ControlFlow::Poll);
}
};

if close_requested {
elwt.exit();
fn start_poll(&mut self, _active: ActiveEventLoop<'_>) {
self.wait_cancelled = false;
}

fn about_to_wait(&mut self, active: ActiveEventLoop<'_>) {
if self.request_redraw && !self.wait_cancelled && !self.close_requested {
self.window.request_redraw();
}

match self.mode {
Mode::Wait => active.set_control_flow(ControlFlow::Wait),
Mode::WaitUntil => {
if !self.wait_cancelled {
active
.set_control_flow(ControlFlow::WaitUntil(time::Instant::now() + WAIT_TIME));
}
}
_ => (),
Mode::Poll => {
thread::sleep(POLL_SLEEP_TIME);
active.set_control_flow(ControlFlow::Poll);
}
};

if self.close_requested {
active.exit();
}
})
}
}

fn main() -> Result<(), impl std::error::Error> {
SimpleLogger::new().init().unwrap();

println!("Press '1' to switch to Wait mode.");
println!("Press '2' to switch to WaitUntil mode.");
println!("Press '3' to switch to Poll mode.");
println!("Press 'R' to toggle request_redraw() calls.");
println!("Press 'Esc' to close the window.");

let event_loop = EventLoop::new().unwrap();

let app = App {
window: WindowBuilder::new()
.with_title(
"Press 1, 2, 3 to change control flow mode. Press R to toggle redraw requests.",
)
.build(&event_loop)
.unwrap(),
mode: Mode::Wait,
request_redraw: false,
wait_cancelled: false,
close_requested: false,
};

event_loop.run_with(app)
}
4 changes: 2 additions & 2 deletions examples/cursor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ fn main() -> Result<(), impl std::error::Error> {

let mut cursor_idx = 0;

event_loop.run(move |event, elwt| {
event_loop.run(move |event, event_loop| {
if let Event::WindowEvent { event, .. } = event {
match event {
WindowEvent::KeyboardInput {
Expand All @@ -42,7 +42,7 @@ fn main() -> Result<(), impl std::error::Error> {
fill::fill_window(&window);
}
WindowEvent::CloseRequested => {
elwt.exit();
event_loop.exit();
}
_ => (),
}
Expand Down
Loading