waker.rs 1.2 KB

1234567891011121314151617181920212223242526272829303132
  1. use crate::ipc::UserWindowEvent;
  2. use futures_util::task::ArcWake;
  3. use std::sync::Arc;
  4. use tao::{event_loop::EventLoopProxy, window::WindowId};
  5. /// Create a waker that will send a poll event to the event loop.
  6. ///
  7. /// This lets the VirtualDom "come up for air" and process events while the main thread is blocked by the WebView.
  8. ///
  9. /// All IO and multithreading lives on other threads. Thanks to tokio's work stealing approach, the main thread can never
  10. /// claim a task while it's blocked by the event loop.
  11. pub fn tao_waker(proxy: EventLoopProxy<UserWindowEvent>, id: WindowId) -> std::task::Waker {
  12. struct DomHandle {
  13. proxy: EventLoopProxy<UserWindowEvent>,
  14. id: WindowId,
  15. }
  16. // this should be implemented by most platforms, but ios is missing this until
  17. // https://github.com/tauri-apps/wry/issues/830 is resolved
  18. unsafe impl Send for DomHandle {}
  19. unsafe impl Sync for DomHandle {}
  20. impl ArcWake for DomHandle {
  21. fn wake_by_ref(arc_self: &Arc<Self>) {
  22. _ = arc_self
  23. .proxy
  24. .send_event(UserWindowEvent::Poll(arc_self.id));
  25. }
  26. }
  27. futures_util::task::waker(Arc::new(DomHandle { id, proxy }))
  28. }