-
-
Notifications
You must be signed in to change notification settings - Fork 176
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #741 from Sharktheone/event-loop/web
- Loading branch information
Showing
11 changed files
with
595 additions
and
90 deletions.
There are no files selected for viewing
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
[package] | ||
name = "gosub_web_platform" | ||
version = "0.1.0" | ||
edition = "2021" | ||
authors = ["Gosub Community <[email protected]>"] | ||
license = "MIT" | ||
description = "Gosub Web Platform implementation" | ||
|
||
[dependencies] | ||
gosub_shared = { version = "0.1.1", registry = "gosub", path = "../gosub_shared" } | ||
gosub_interface = { version = "0.1.2", registry = "gosub", path = "../gosub_interface", features = [] } | ||
slotmap = "1.0.7" | ||
tokio = { version = "1.42.0", features = ["sync", "rt", "macros"] } | ||
pin-project = "1.1.7" | ||
log = "0.4.22" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
use crate::poll_guard::{PollCallback, PollGuard}; | ||
use std::future::Future; | ||
use tokio::task; | ||
|
||
struct TestPollGuard; | ||
|
||
impl PollCallback for TestPollGuard { | ||
fn poll(&mut self) { | ||
//TODO: execute the js microtasks | ||
} | ||
} | ||
|
||
pub trait FutureExecutor { | ||
fn execute<T: Future<Output = ()> + 'static>(&mut self, future: T); | ||
} | ||
|
||
pub struct Callback<T: FutureExecutor, D = ()> { | ||
#[allow(clippy::type_complexity)] | ||
spawner: Box<dyn FnMut(&mut T, D)>, | ||
} | ||
|
||
impl<T: FutureExecutor, D> Callback<T, D> { | ||
pub fn new(spawner: impl FnMut(&mut T, D) + 'static) -> Self { | ||
Self { | ||
spawner: Box::new(spawner), | ||
} | ||
} | ||
|
||
pub fn execute(&mut self, executor: &mut T, data: D) { | ||
(self.spawner)(executor, data); | ||
} | ||
} | ||
|
||
impl<T: FutureExecutor> Callback<T> { | ||
pub fn exec(&mut self, executor: &mut T) { | ||
self.execute(executor, ()); | ||
} | ||
} | ||
|
||
#[derive(Debug, Default)] | ||
pub struct TokioExecutor; | ||
|
||
impl FutureExecutor for TokioExecutor { | ||
fn execute<T: Future<Output = ()> + 'static>(&mut self, future: T) { | ||
let guard = PollGuard::new(future, TestPollGuard); | ||
|
||
task::spawn_local(guard); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,132 @@ | ||
use crate::callback::{Callback, FutureExecutor}; | ||
use gosub_interface::input::{InputEvent, MouseButton}; | ||
use gosub_shared::geo::Point; | ||
use log::info; | ||
use std::fmt::Debug; | ||
|
||
pub enum Listeners<E: FutureExecutor> { | ||
MouseDown(Callback<E, MouseButtonEvent>), | ||
MouseUp(Callback<E, MouseButtonEvent>), | ||
MouseMove(Callback<E, MouseMoveEvent>), | ||
MouseScroll(Callback<E, MouseScrollEvent>), | ||
KeyboardUp(Callback<E, KeyboardEvent>), | ||
KeyboardDown(Callback<E, KeyboardEvent>), | ||
} | ||
|
||
#[derive(Debug, Clone, Copy)] | ||
pub struct MouseButtonEvent { | ||
pub button: MouseButton, | ||
} | ||
|
||
#[derive(Debug, Clone, Copy)] | ||
pub struct KeyboardEvent { | ||
pub key: char, | ||
} | ||
|
||
#[derive(Debug, Clone, Copy)] | ||
pub struct MouseMoveEvent { | ||
pub pos: Point, | ||
} | ||
|
||
#[derive(Debug, Clone, Copy)] | ||
pub struct MouseScrollEvent { | ||
pub delta: Point, | ||
} | ||
|
||
pub struct EventListener<D, E: FutureExecutor> { | ||
listeners: Vec<Callback<E, D>>, | ||
} | ||
|
||
impl<D: Clone + Debug, E: FutureExecutor> EventListener<D, E> { | ||
pub fn handle_event(&mut self, event: D, e: &mut E) { | ||
info!("Handling event: {:?}", event); | ||
for listener in self.listeners.iter_mut() { | ||
listener.execute(e, event.clone()); | ||
} | ||
} | ||
} | ||
|
||
impl<D, E: FutureExecutor> Debug for EventListener<D, E> { | ||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { | ||
f.debug_struct("EventListener") | ||
.field("listeners", &self.listeners.len()) | ||
.finish() | ||
} | ||
} | ||
|
||
impl<D, E: FutureExecutor> Default for EventListener<D, E> { | ||
fn default() -> Self { | ||
Self { listeners: Vec::new() } | ||
} | ||
} | ||
|
||
pub struct EventListeners<E: FutureExecutor> { | ||
mouse_up: EventListener<MouseButtonEvent, E>, | ||
mouse_down: EventListener<MouseButtonEvent, E>, | ||
mouse_move: EventListener<MouseMoveEvent, E>, | ||
mouse_scroll: EventListener<MouseScrollEvent, E>, | ||
keyboard_up: EventListener<KeyboardEvent, E>, | ||
keyboard_down: EventListener<KeyboardEvent, E>, | ||
} | ||
|
||
impl<E: FutureExecutor> EventListeners<E> { | ||
pub(crate) fn add_listener(&mut self, listener: Listeners<E>) { | ||
match listener { | ||
Listeners::MouseDown(callback) => self.mouse_down.listeners.push(callback), | ||
Listeners::MouseUp(callback) => self.mouse_up.listeners.push(callback), | ||
Listeners::MouseMove(callback) => self.mouse_move.listeners.push(callback), | ||
Listeners::MouseScroll(callback) => self.mouse_scroll.listeners.push(callback), | ||
Listeners::KeyboardUp(callback) => self.keyboard_up.listeners.push(callback), | ||
Listeners::KeyboardDown(callback) => self.keyboard_down.listeners.push(callback), | ||
} | ||
} | ||
|
||
pub(crate) fn handle_input_event(&mut self, event: InputEvent, e: &mut E) { | ||
match event { | ||
InputEvent::MouseDown(button) => { | ||
self.mouse_down.handle_event(MouseButtonEvent { button }, e); | ||
} | ||
InputEvent::MouseUp(button) => { | ||
self.mouse_up.handle_event(MouseButtonEvent { button }, e); | ||
} | ||
InputEvent::MouseMove(pos) => { | ||
self.mouse_move.handle_event(MouseMoveEvent { pos }, e); | ||
} | ||
InputEvent::MouseScroll(delta) => { | ||
self.mouse_scroll.handle_event(MouseScrollEvent { delta }, e); | ||
} | ||
InputEvent::KeyboardDown(key) => { | ||
self.keyboard_down.handle_event(KeyboardEvent { key }, e); | ||
} | ||
InputEvent::KeyboardUp(key) => { | ||
self.keyboard_up.handle_event(KeyboardEvent { key }, e); | ||
} | ||
} | ||
} | ||
} | ||
|
||
impl<E: FutureExecutor> Default for EventListeners<E> { | ||
fn default() -> Self { | ||
Self { | ||
mouse_up: EventListener::default(), | ||
mouse_down: EventListener::default(), | ||
mouse_move: EventListener::default(), | ||
mouse_scroll: EventListener::default(), | ||
keyboard_up: EventListener::default(), | ||
keyboard_down: EventListener::default(), | ||
} | ||
} | ||
} | ||
|
||
impl<E: FutureExecutor> Debug for EventListeners<E> { | ||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { | ||
f.debug_struct("EventListeners") | ||
.field("mouse_down", &self.mouse_down) | ||
.field("mouse_up", &self.mouse_up) | ||
.field("mouse_move", &self.mouse_move) | ||
.field("mouse_scroll", &self.mouse_scroll) | ||
.field("keyboard_down", &self.keyboard_down) | ||
.field("keyboard_up", &self.keyboard_up) | ||
.finish() | ||
} | ||
} |
Oops, something went wrong.