mirror of
https://github.com/italicsjenga/winit-sonoma-fix.git
synced 2024-12-25 06:41:31 +11:00
Implement WindowID on the web platform (#1177)
* Use actual numeric IDs to differentiate Windows This is generally important to identifying which window should recieve which event, but is also specifically crucial for fixing RedrawRequested on web. * Cargo fmt
This commit is contained in:
parent
e87bc3db20
commit
2c47c43f47
|
@ -16,6 +16,7 @@ impl<T> Clone for Shared<T> {
|
||||||
pub struct Execution<T> {
|
pub struct Execution<T> {
|
||||||
runner: RefCell<Option<Runner<T>>>,
|
runner: RefCell<Option<Runner<T>>>,
|
||||||
events: RefCell<VecDeque<Event<T>>>,
|
events: RefCell<VecDeque<Event<T>>>,
|
||||||
|
id: RefCell<u32>,
|
||||||
}
|
}
|
||||||
|
|
||||||
struct Runner<T> {
|
struct Runner<T> {
|
||||||
|
@ -39,6 +40,7 @@ impl<T: 'static> Shared<T> {
|
||||||
Shared(Rc::new(Execution {
|
Shared(Rc::new(Execution {
|
||||||
runner: RefCell::new(None),
|
runner: RefCell::new(None),
|
||||||
events: RefCell::new(VecDeque::new()),
|
events: RefCell::new(VecDeque::new()),
|
||||||
|
id: RefCell::new(0),
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -53,6 +55,15 @@ impl<T: 'static> Shared<T> {
|
||||||
backend::on_unload(move || close_instance.handle_unload());
|
backend::on_unload(move || close_instance.handle_unload());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Generate a strictly increasing ID
|
||||||
|
// This is used to differentiate windows when handling events
|
||||||
|
pub fn generate_id(&self) -> u32 {
|
||||||
|
let mut id = self.0.id.borrow_mut();
|
||||||
|
*id += 1;
|
||||||
|
|
||||||
|
*id
|
||||||
|
}
|
||||||
|
|
||||||
// Add an event to the event loop runner
|
// Add an event to the event loop runner
|
||||||
//
|
//
|
||||||
// It will determine if the event should be immediately sent to the user or buffered for later
|
// It will determine if the event should be immediately sent to the user or buffered for later
|
||||||
|
|
|
@ -31,11 +31,16 @@ impl<T> WindowTarget<T> {
|
||||||
self.runner.set_listener(event_handler);
|
self.runner.set_listener(event_handler);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn register(&self, canvas: &mut backend::Canvas) {
|
pub fn generate_id(&self) -> window::Id {
|
||||||
|
window::Id(self.runner.generate_id())
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn register(&self, canvas: &mut backend::Canvas, id: window::Id) {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
|
|
||||||
canvas.on_blur(move || {
|
canvas.on_blur(move || {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::Focused(false),
|
event: WindowEvent::Focused(false),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -43,7 +48,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_focus(move || {
|
canvas.on_focus(move || {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::Focused(true),
|
event: WindowEvent::Focused(true),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -51,7 +56,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_keyboard_press(move |scancode, virtual_keycode, modifiers| {
|
canvas.on_keyboard_press(move |scancode, virtual_keycode, modifiers| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::KeyboardInput {
|
event: WindowEvent::KeyboardInput {
|
||||||
device_id: DeviceId(unsafe { device::Id::dummy() }),
|
device_id: DeviceId(unsafe { device::Id::dummy() }),
|
||||||
input: KeyboardInput {
|
input: KeyboardInput {
|
||||||
|
@ -67,7 +72,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_keyboard_release(move |scancode, virtual_keycode, modifiers| {
|
canvas.on_keyboard_release(move |scancode, virtual_keycode, modifiers| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::KeyboardInput {
|
event: WindowEvent::KeyboardInput {
|
||||||
device_id: DeviceId(unsafe { device::Id::dummy() }),
|
device_id: DeviceId(unsafe { device::Id::dummy() }),
|
||||||
input: KeyboardInput {
|
input: KeyboardInput {
|
||||||
|
@ -83,7 +88,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_received_character(move |char_code| {
|
canvas.on_received_character(move |char_code| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::ReceivedCharacter(char_code),
|
event: WindowEvent::ReceivedCharacter(char_code),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -91,7 +96,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_cursor_leave(move |pointer_id| {
|
canvas.on_cursor_leave(move |pointer_id| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::CursorLeft {
|
event: WindowEvent::CursorLeft {
|
||||||
device_id: DeviceId(device::Id(pointer_id)),
|
device_id: DeviceId(device::Id(pointer_id)),
|
||||||
},
|
},
|
||||||
|
@ -101,7 +106,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_cursor_enter(move |pointer_id| {
|
canvas.on_cursor_enter(move |pointer_id| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::CursorEntered {
|
event: WindowEvent::CursorEntered {
|
||||||
device_id: DeviceId(device::Id(pointer_id)),
|
device_id: DeviceId(device::Id(pointer_id)),
|
||||||
},
|
},
|
||||||
|
@ -111,7 +116,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_cursor_move(move |pointer_id, position, modifiers| {
|
canvas.on_cursor_move(move |pointer_id, position, modifiers| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::CursorMoved {
|
event: WindowEvent::CursorMoved {
|
||||||
device_id: DeviceId(device::Id(pointer_id)),
|
device_id: DeviceId(device::Id(pointer_id)),
|
||||||
position,
|
position,
|
||||||
|
@ -123,7 +128,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_mouse_press(move |pointer_id, button, modifiers| {
|
canvas.on_mouse_press(move |pointer_id, button, modifiers| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::MouseInput {
|
event: WindowEvent::MouseInput {
|
||||||
device_id: DeviceId(device::Id(pointer_id)),
|
device_id: DeviceId(device::Id(pointer_id)),
|
||||||
state: ElementState::Pressed,
|
state: ElementState::Pressed,
|
||||||
|
@ -136,7 +141,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_mouse_release(move |pointer_id, button, modifiers| {
|
canvas.on_mouse_release(move |pointer_id, button, modifiers| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::MouseInput {
|
event: WindowEvent::MouseInput {
|
||||||
device_id: DeviceId(device::Id(pointer_id)),
|
device_id: DeviceId(device::Id(pointer_id)),
|
||||||
state: ElementState::Released,
|
state: ElementState::Released,
|
||||||
|
@ -149,7 +154,7 @@ impl<T> WindowTarget<T> {
|
||||||
let runner = self.runner.clone();
|
let runner = self.runner.clone();
|
||||||
canvas.on_mouse_wheel(move |pointer_id, delta, modifiers| {
|
canvas.on_mouse_wheel(move |pointer_id, delta, modifiers| {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: WindowId(window::Id),
|
window_id: WindowId(id),
|
||||||
event: WindowEvent::MouseWheel {
|
event: WindowEvent::MouseWheel {
|
||||||
device_id: DeviceId(device::Id(pointer_id)),
|
device_id: DeviceId(device::Id(pointer_id)),
|
||||||
delta,
|
delta,
|
||||||
|
|
|
@ -13,7 +13,7 @@ use stdweb::web::event::{
|
||||||
};
|
};
|
||||||
use stdweb::web::html_element::CanvasElement;
|
use stdweb::web::html_element::CanvasElement;
|
||||||
use stdweb::web::{
|
use stdweb::web::{
|
||||||
document, window, EventListenerHandle, IChildNode, IElement, IEventTarget, IHtmlElement, INode,
|
document, window, EventListenerHandle, IChildNode, IElement, IEventTarget, IHtmlElement,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub struct Canvas {
|
pub struct Canvas {
|
||||||
|
|
|
@ -15,6 +15,7 @@ pub struct Window {
|
||||||
canvas: backend::Canvas,
|
canvas: backend::Canvas,
|
||||||
previous_pointer: RefCell<&'static str>,
|
previous_pointer: RefCell<&'static str>,
|
||||||
position: RefCell<LogicalPosition>,
|
position: RefCell<LogicalPosition>,
|
||||||
|
id: Id,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Window {
|
impl Window {
|
||||||
|
@ -25,19 +26,22 @@ impl Window {
|
||||||
) -> Result<Self, RootOE> {
|
) -> Result<Self, RootOE> {
|
||||||
let runner = target.runner.clone();
|
let runner = target.runner.clone();
|
||||||
|
|
||||||
|
let id = target.generate_id();
|
||||||
|
|
||||||
let mut canvas = backend::Canvas::create(move || {
|
let mut canvas = backend::Canvas::create(move || {
|
||||||
runner.send_event(Event::WindowEvent {
|
runner.send_event(Event::WindowEvent {
|
||||||
window_id: RootWI(Id),
|
window_id: RootWI(id),
|
||||||
event: WindowEvent::RedrawRequested,
|
event: WindowEvent::RedrawRequested,
|
||||||
})
|
})
|
||||||
})?;
|
})?;
|
||||||
|
|
||||||
target.register(&mut canvas);
|
target.register(&mut canvas, id);
|
||||||
|
|
||||||
let window = Window {
|
let window = Window {
|
||||||
canvas,
|
canvas,
|
||||||
previous_pointer: RefCell::new("auto"),
|
previous_pointer: RefCell::new("auto"),
|
||||||
position: RefCell::new(LogicalPosition { x: 0.0, y: 0.0 }),
|
position: RefCell::new(LogicalPosition { x: 0.0, y: 0.0 }),
|
||||||
|
id,
|
||||||
};
|
};
|
||||||
|
|
||||||
window.set_inner_size(attr.inner_size.unwrap_or(LogicalSize {
|
window.set_inner_size(attr.inner_size.unwrap_or(LogicalSize {
|
||||||
|
@ -250,17 +254,16 @@ impl Window {
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn id(&self) -> Id {
|
pub fn id(&self) -> Id {
|
||||||
// TODO ?
|
return self.id;
|
||||||
unsafe { Id::dummy() }
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Copy, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
#[derive(Debug, Copy, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
||||||
pub struct Id;
|
pub struct Id(pub(crate) u32);
|
||||||
|
|
||||||
impl Id {
|
impl Id {
|
||||||
pub unsafe fn dummy() -> Id {
|
pub unsafe fn dummy() -> Id {
|
||||||
Id
|
Id(0)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue