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

MacOS ControlFlow::Wait doesn't work properly when pointer leaves window #3934

Open
ocheret opened this issue Sep 30, 2024 · 13 comments
Open
Labels
B - bug Dang, that shouldn't have happened DS - macos

Comments

@ocheret
Copy link

ocheret commented Sep 30, 2024

Description

When implementing ApplicationHandler I implemented my own about_to_wait() method. When control flow is set to ControlFlow::Wait and the pointer remains within the window, everything works as expected - the thread goes to sleep when nothing is happening. However, when the pointer leaves the window, the about_to_wait() method is called non-stop as if control flow was set to ControlFlow::Poll. When the pointer reenters the window, things work as expected again.

Super simple code example:

use winit::application::ApplicationHandler;
use winit::event::WindowEvent;
use winit::event_loop::{ActiveEventLoop, ControlFlow, EventLoop};
use winit::window::{Window, WindowAttributes, WindowId};

#[derive(Debug, Default)]
struct App {
    window: Option<Window>,
}

impl ApplicationHandler for App {
    fn resumed(&mut self, event_loop: &ActiveEventLoop) {
        if self.window.is_none() {
            let window = event_loop
                .create_window(WindowAttributes::default())
                .expect("Failed to create window");
            self.window = Some(window);
        }
        println!("resumed");
    }

    fn window_event(
        &mut self,
        event_loop: &ActiveEventLoop,
        window_id: WindowId,
        event: WindowEvent,
    ) {
        println!("window_event: {:?}", event);
    }

    // When the pointer leaves the window, this is called incessantly!
    fn about_to_wait(&mut self, event_loop: &ActiveEventLoop) {
        println!("about_to_wait");
    }
}

fn main() {
    let event_loop = EventLoop::new().expect("Failed to create event loop");
    event_loop.set_control_flow(ControlFlow::Wait);

    let mut app = App::default();
    event_loop.run_app(&mut app).expect("Failed to run app");
}

macOS version

ProductName:            macOS
ProductVersion:         14.6.1
BuildVersion:           23G93

Winit version

0.30.5

@ocheret ocheret added B - bug Dang, that shouldn't have happened DS - macos labels Sep 30, 2024
@kchibisov
Copy link
Member

Does it happen with the window example?

@ocheret
Copy link
Author

ocheret commented Sep 30, 2024

Hard to say. That example doesn't seem to open a window (I can't locate it on a screen anyway) and it also doesn't appear to call set_control_flow. Or maybe I'm missing something.

@kchibisov
Copy link
Member

Are you sure that it doesn't open anything at all? It should open a window and lists you some key bindings to press.

The default control flow is Wait, so it's what it's using, you don't have to explicitly set anything.

@ocheret
Copy link
Author

ocheret commented Sep 30, 2024

Ok, had to get a desktop view - the window shows up behind the terminal I was using. I added an info! call to the about_to_wait call in there (it wasn't logging anything normally). I do not see the behavior there. :-(

My code snippet is quite short. Is there anything obvious that I'm doing wrong in there? I removed my set_control_flow call (to get the default behavior) and I see the same result. Is there some other option I need to set?

@kchibisov
Copy link
Member

maybe not drawing anything ends up like that, because macOS is confused. Also if you don't set ControlFlow to anything does it change behavior (it shouldn't, but just in case)?

@ocheret
Copy link
Author

ocheret commented Sep 30, 2024

Not setting ControlFlow results in the same behavior as explicitly setting it to Wait (as you said it would). Basically, I'm trying to come up with bare-bones examples and build up slowly for a tutorial. Ultimately, I'm trying to get a good set of wgpu examples working with the latest winit (everything I can find out that uses older versions) and also illustrate integration with Tokio (among other things). Today was my first deep dive into 0.30.* and the docs are not super helpful. I'm happy to help improve them and provide more general tutorials if I can get it all figured out.

@ocheret
Copy link
Author

ocheret commented Sep 30, 2024

Even GitHub Copilot begs me to use an older version. ;-)

@kchibisov
Copy link
Member

I mean, your provided code should generally work and I think it does. If macOS wakes you up, it's mostly up to it and given that our example also works, the issue could you not doing any drawing, so I'd suggest to draw something(even with softbuffer) and problem will likely go away.

0.30 and 0.29 don't differ much other than big callback vs trait, the rest is entirely the same, so wgpu examples for 0.29 will work fine. You can also look into glutin examples, it's using 0.30.

@kchibisov
Copy link
Member

@madsmtm do you know what the issue could be on macOS? I'd guess macOS compositor tries to ask for drawing and no drawing ever done so it kind of loops?

@ocheret
Copy link
Author

ocheret commented Oct 1, 2024

I think I've been comparing apples and oranges. I've been trying to use v0.30.5, which is what I'm getting as the latest on crates.io for my test program. I was comparing that against master when running the window.rs example from GitHub. It is very different (e.g. create_window returns a Window in 0.30.5 but a Box(dyn Window) in master). When I look at the window.rs example from 0.30.5 it is completely different - it doesn't even use the ApplicationHandler trait. So I think I'm completely lost now. What should I be using?

@kchibisov
Copy link
Member

latest released version.

@ocheret
Copy link
Author

ocheret commented Oct 1, 2024

Ok, so the problem seems to exist there (v0.30.5).

@kchibisov
Copy link
Member

I mean, I know that none of the examples that draw has this issue, otherwise I'd know it. So as I said, as soon as you start drawing it should go away.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
B - bug Dang, that shouldn't have happened DS - macos
Development

No branches or pull requests

2 participants