diff options
author | Matthew Michelotti <michelotti.matthew@gmail.com> | 2018-05-05 11:08:37 -0500 |
---|---|---|
committer | Matthew Michelotti <michelotti.matthew@gmail.com> | 2018-05-05 13:32:04 -0500 |
commit | 2dbc4f3e11dcd28d8e1ff26693afaf73ac7922fc (patch) | |
tree | 735f8f1605c2e9056557314dc0f36170ee539841 | |
parent | 85f7596016cd07452c9c3349ececbd59b6ba96da (diff) |
tracking mouse position in AppContext
-rw-r--r-- | example/src/main.rs | 2 | ||||
-rw-r--r-- | gate/src/core/sdl/event_handler.rs | 12 | ||||
-rw-r--r-- | gate/src/core/sdl/mod.rs | 4 | ||||
-rw-r--r-- | gate/src/core/wasm/mod.rs | 20 | ||||
-rw-r--r-- | gate/src/core/wasm/wasm_exports.rs | 4 | ||||
-rw-r--r-- | gate/src/lib.rs | 12 | ||||
-rw-r--r-- | gate/src/renderer/render_buffer.rs | 23 | ||||
-rw-r--r-- | gate/src/renderer/renderer.rs | 4 | ||||
-rw-r--r-- | gate_build/src/html/gate.js | 10 |
9 files changed, 61 insertions, 30 deletions
diff --git a/example/src/main.rs b/example/src/main.rs index 6cbf9d3..f6b4bcb 100644 --- a/example/src/main.rs +++ b/example/src/main.rs @@ -86,7 +86,7 @@ impl App<AssetId> for TowerGame { } } - fn render(&mut self, renderer: &mut Renderer<AssetId>) { + fn render(&mut self, renderer: &mut Renderer<AssetId>, _ctx: &AppContext<AssetId>) { let (app_width, app_height) = renderer.app_dims(); { // drawing tiles let mut renderer = renderer.tiled_mode(0.5 * app_width, 0.5 * app_height); diff --git a/gate/src/core/sdl/event_handler.rs b/gate/src/core/sdl/event_handler.rs index bf9d478..27110c7 100644 --- a/gate/src/core/sdl/event_handler.rs +++ b/gate/src/core/sdl/event_handler.rs @@ -18,10 +18,10 @@ use sdl2::EventPump; use sdl2::event::Event; use sdl2::keyboard::Keycode as SdlKeyCode; -use ::App; -use ::AppContext; -use ::asset_id::AppAssetId; -use ::input::{KeyEvent, KeyCode}; +use ::{App, AppContext}; +use asset_id::AppAssetId; +use input::{KeyEvent, KeyCode}; +use renderer::Renderer; pub struct EventHandler { pump: EventPump, @@ -33,7 +33,8 @@ impl EventHandler { EventHandler { pump, held_keys: HashSet::new() } } - pub fn process_events<AS: AppAssetId, AP: App<AS>>(&mut self, app: &mut AP, ctx: &mut AppContext<AS>) { + pub fn process_events<AS: AppAssetId, AP: App<AS>>(&mut self, app: &mut AP, ctx: &mut AppContext<AS>, + renderer: &Renderer<AS>) { for event in self.pump.poll_iter() { match event { Event::Quit { .. } => ctx.close(), @@ -51,6 +52,7 @@ impl EventHandler { } } }, + Event::MouseMotion { x, y, .. } => ctx.cursor = renderer.to_app_pos(x, y), _ => {}, } if ctx.close_requested { break; } diff --git a/gate/src/core/sdl/mod.rs b/gate/src/core/sdl/mod.rs index 2f4badf..c0fd3f9 100644 --- a/gate/src/core/sdl/mod.rs +++ b/gate/src/core/sdl/mod.rs @@ -92,7 +92,7 @@ pub fn run<AS: AppAssetId, AP: App<AS>>(info: AppInfo, mut app: AP) { if screen_dims.0 >= MIN_WINDOW_SIZE && screen_dims.1 >= MIN_WINDOW_SIZE { renderer.set_screen_dims(screen_dims); ctx.dims = renderer.app_dims(); - app.render(&mut renderer); + app.render(&mut renderer, &ctx); renderer.flush(); } sdl_renderer.present(); @@ -100,7 +100,7 @@ pub fn run<AS: AppAssetId, AP: App<AS>>(info: AppInfo, mut app: AP) { let elapsed = clock.step(); - event_handler.process_events(&mut app, &mut ctx); + event_handler.process_events(&mut app, &mut ctx, &renderer); if ctx.close_requested { break; } app.advance(elapsed, &mut ctx); if ctx.close_requested { break; } diff --git a/gate/src/core/wasm/mod.rs b/gate/src/core/wasm/mod.rs index 28993cf..2521ad3 100644 --- a/gate/src/core/wasm/mod.rs +++ b/gate/src/core/wasm/mod.rs @@ -55,7 +55,7 @@ impl CoreAudio { trait TraitAppRunner { fn init(&mut self); fn resize(&mut self, dims: (u32, u32)); - fn update_and_draw(&mut self, time_sec: f64); + fn update_and_draw(&mut self, time_sec: f64, cursor_x: i32, cursor_y: i32); fn input(&mut self, event: KeyEvent, key: KeyCode); fn music_count(&self) -> u16; fn sound_count(&self) -> u16; @@ -86,6 +86,7 @@ struct AppRunner<AS: AppAssetId, AP: App<AS>> { app: AP, info: AppInfo, renderer: Option<Renderer<AS>>, + ctx: AppContext<AS>, last_time_sec: Option<f64>, held_keys: HashSet<KeyCode>, } @@ -111,35 +112,35 @@ impl<AS: AppAssetId, AP: App<AS>> TraitAppRunner for AppRunner<AS, AP> { let core_renderer = CoreRenderer::new(&render_buffer); self.renderer = Some(Renderer::<AS>::new(render_buffer, core_renderer)); - let mut ctx = AppContext::new(CoreAudio { }, self.renderer.as_ref().unwrap().app_dims()); - self.app.start(&mut ctx); + self.ctx.dims = self.renderer.as_ref().unwrap().app_dims(); + self.app.start(&mut self.ctx); } fn resize(&mut self, dims: (u32, u32)) { self.renderer.as_mut().unwrap().set_screen_dims(dims); + self.ctx.dims = self.renderer.as_ref().unwrap().app_dims(); } - fn update_and_draw(&mut self, time_sec: f64) { - let mut ctx = AppContext::new(CoreAudio { }, self.renderer.as_ref().unwrap().app_dims()); + fn update_and_draw(&mut self, time_sec: f64, cursor_x: i32, cursor_y: i32) { + self.ctx.cursor = self.renderer.as_ref().unwrap().to_app_pos(cursor_x, cursor_y); let elapsed = self.last_time_sec.map(|x| time_sec - x).unwrap_or(0.0).max(0.0).min(0.1); if elapsed > 0.0 { - self.app.advance(elapsed, &mut ctx); + self.app.advance(elapsed, &mut self.ctx); } self.last_time_sec = Some(time_sec); - self.app.render(self.renderer.as_mut().unwrap()); + self.app.render(self.renderer.as_mut().unwrap(), &self.ctx); self.renderer.as_mut().unwrap().flush(); } fn input(&mut self, event: KeyEvent, key: KeyCode) { - let mut ctx = AppContext::new(CoreAudio { }, self.renderer.as_ref().unwrap().app_dims()); let success = if event == KeyEvent::Pressed { self.held_keys.insert(key) } else { self.held_keys.remove(&key) }; if success { - self.app.input(event, key, &mut ctx); + self.app.input(event, key, &mut self.ctx); } } @@ -151,6 +152,7 @@ pub fn run<AS: 'static + AppAssetId, AP: 'static + App<AS>>(info: AppInfo, app: mark_app_created_flag(); *APP_RUNNER.r.borrow_mut() = Some(Box::new(AppRunner { app, info, + ctx: AppContext::new(CoreAudio { }, (0., 0.)), renderer: None, last_time_sec: None, held_keys: HashSet::new(), diff --git a/gate/src/core/wasm/wasm_exports.rs b/gate/src/core/wasm/wasm_exports.rs index db27db3..0e51f1e 100644 --- a/gate/src/core/wasm/wasm_exports.rs +++ b/gate/src/core/wasm/wasm_exports.rs @@ -32,8 +32,8 @@ pub unsafe extern "C" fn gateWasmOnResize(w: c_int, h: c_int) { } #[no_mangle] -pub unsafe extern "C" fn gateWasmUpdateAndDraw(time_millis: f64) { - app_runner_borrow_mut().update_and_draw(time_millis / 1000.0); +pub unsafe extern "C" fn gateWasmUpdateAndDraw(time_millis: f64, cursor_x: c_int, cursor_y: c_int) { + app_runner_borrow_mut().update_and_draw(time_millis / 1000.0, cursor_x as i32, cursor_y as i32); } #[no_mangle] diff --git a/gate/src/lib.rs b/gate/src/lib.rs index 4fc7b4d..cf0a7e9 100644 --- a/gate/src/lib.rs +++ b/gate/src/lib.rs @@ -90,20 +90,28 @@ pub trait App<A: AppAssetId> { fn input(&mut self, event: KeyEvent, key: KeyCode, ctx: &mut AppContext<A>); /// Render the app in its current state. - fn render(&mut self, renderer: &mut Renderer<A>); + fn render(&mut self, renderer: &mut Renderer<A>, ctx: &AppContext<A>); } -pub struct AppContext<A: AppAssetId> { pub audio: Audio<A>, dims: (f64, f64), close_requested: bool } +pub struct AppContext<A: AppAssetId> { + pub audio: Audio<A>, + dims: (f64, f64), + cursor: (f64, f64), + close_requested: bool, +} impl<A: AppAssetId> AppContext<A> { pub(crate) fn new(audio: CoreAudio, dims: (f64, f64)) -> AppContext<A> { AppContext { audio: Audio { core: audio, phantom: PhantomData }, dims, + cursor: (0., 0.), close_requested: false, } } + pub fn cursor(&self) -> (f64, f64) { self.cursor } + pub fn dims(&self) -> (f64, f64) { self.dims } pub fn close(&mut self) { self.close_requested = true; } diff --git a/gate/src/renderer/render_buffer.rs b/gate/src/renderer/render_buffer.rs index c216fc4..a9651db 100644 --- a/gate/src/renderer/render_buffer.rs +++ b/gate/src/renderer/render_buffer.rs @@ -32,13 +32,13 @@ impl Mode { } pub(super) struct RenderDims { - pub(super) min_aspect_ratio: f64, - pub(super) max_aspect_ratio: f64, - pub(super) app_dims: (f64, f64), - pub(super) full_screen_dims: (u32, u32), - pub(super) tiled_fbo_dims: (u32, u32), - pub(super) used_screen_dims: (u32, u32), - pub(super) app_pixel_scalar: f64, + pub min_aspect_ratio: f64, + pub max_aspect_ratio: f64, + pub app_dims: (f64, f64), + pub full_screen_dims: (u32, u32), + pub tiled_fbo_dims: (u32, u32), + pub used_screen_dims: (u32, u32), + pub app_pixel_scalar: f64, } impl RenderDims { @@ -68,9 +68,16 @@ impl RenderDims { } } - pub(super) fn set_full_screen_dims(&mut self, screen_dims: (u32, u32)) { + pub fn set_full_screen_dims(&mut self, screen_dims: (u32, u32)) { *self = RenderDims::new(self.min_aspect_ratio, self.max_aspect_ratio, self.app_dims.1, screen_dims); } + + pub fn to_app_pos(&self, raw_x: i32, raw_y: i32) -> (f64, f64) { + let x = (raw_x as f64 - 0.5 * self.full_screen_dims.0 as f64) / self.app_pixel_scalar; + let y = -(raw_y as f64 - 0.5 * self.full_screen_dims.1 as f64) / self.app_pixel_scalar; + let (half_width, half_height) = (self.app_dims.0 * 0.5, self.app_dims.1 * 0.5); + (x.max(-half_width).min(half_width), y.max(-half_height).min(half_height)) + } } fn to_fbo_dim(app_dim: f64) -> u32 { diff --git a/gate/src/renderer/renderer.rs b/gate/src/renderer/renderer.rs index e76cb9b..acf9bb5 100644 --- a/gate/src/renderer/renderer.rs +++ b/gate/src/renderer/renderer.rs @@ -67,6 +67,10 @@ impl<A: AppAssetId> Renderer<A> { pub fn app_dims(&self) -> (f64, f64) { self.b.dims.app_dims } + pub(crate) fn to_app_pos(&self, raw_x: i32, raw_y: i32) -> (f64, f64) { + self.b.dims.to_app_pos(raw_x, raw_y) + } + pub(crate) fn flush(&mut self) { self.b.flush(&mut self.c); } diff --git a/gate_build/src/html/gate.js b/gate_build/src/html/gate.js index 77c80d7..2329cbb 100644 --- a/gate_build/src/html/gate.js +++ b/gate_build/src/html/gate.js @@ -53,6 +53,8 @@ gl.blendFunc(gl.ONE, gl.ONE_MINUS_SRC_ALPHA); var vbo = gl.createBuffer(); gl.bindBuffer(gl.ARRAY_BUFFER, vbo); +var cursorPos = { x: 0, y: 0 }; + var Module = {}; Module.loadingAudioCount = 0; @@ -409,12 +411,13 @@ function tryStart2 () { requestAnimationFrame(updateAndDraw); document.addEventListener('keydown', e => handleKeyEvent(e.key, true)); document.addEventListener('keyup', e => handleKeyEvent(e.key, false)); + document.addEventListener('mousemove', e => handleMouseMotionEvent(e)); } } function updateAndDraw(now) { resizeCanvas(); - Module.gateWasmUpdateAndDraw(now); + Module.gateWasmUpdateAndDraw(now, cursorPos.x, cursorPos.y); requestAnimationFrame(updateAndDraw); } @@ -425,6 +428,11 @@ function handleKeyEvent(codeStr, down) { } } +function handleMouseMotionEvent(evt) { + cursorPos.x = evt.clientX; + cursorPos.y = evt.clientY; +} + function resizeCanvas() { const newWidth = Math.max(window.innerWidth, 100); const newHeight = Math.max(window.innerHeight, 100); |