diff --git a/neothesia/src/main.rs b/neothesia/src/main.rs index ed60a1cc..1f4c385a 100644 --- a/neothesia/src/main.rs +++ b/neothesia/src/main.rs @@ -20,7 +20,7 @@ use neothesia_core::{config, render}; use wgpu_jumpstart::{Gpu, Surface, TransformUniform}; use winit::{ application::ApplicationHandler, - event::WindowEvent, + event::{ElementState, MouseButton, TouchPhase, WindowEvent}, event_loop::{EventLoop, EventLoopProxy}, keyboard::NamedKey, }; @@ -71,6 +71,41 @@ impl Neothesia { _window_id: winit::window::WindowId, event: WindowEvent, ) { + if let WindowEvent::Touch(touch) = &event { + + // 1) Feed a CursorMoved equivalent (important for hit testing) + let cursor_ev = WindowEvent::CursorMoved { + device_id: touch.device_id, + position: touch.location, + // If your winit version requires extra fields here (e.g. modifiers), + // the compiler will tell you. Add them based on the type error. + }; + + self.context.window_state.window_event(&cursor_ev); + self.game_scene.window_event(&mut self.context, &cursor_ev); + + // 2) Feed a synthetic left mouse press/release on touch start/end + let maybe_state = match touch.phase { + TouchPhase::Started => Some(ElementState::Pressed), + TouchPhase::Ended | TouchPhase::Cancelled => Some(ElementState::Released), + TouchPhase::Moved => None, + }; + + if let Some(state) = maybe_state { + let mouse_ev = WindowEvent::MouseInput { + device_id: touch.device_id, + state, + button: MouseButton::Left, + // Same note: if your winit version requires modifiers here, add them. + }; + + self.context.window_state.window_event(&mouse_ev); + self.game_scene.window_event(&mut self.context, &mouse_ev); + } + + // Don’t also pass through the raw Touch event. + return; + } self.context.window_state.window_event(&event); match &event { diff --git a/neothesia/src/utils/window.rs b/neothesia/src/utils/window.rs index 4cf81a09..c0eb492b 100644 --- a/neothesia/src/utils/window.rs +++ b/neothesia/src/utils/window.rs @@ -6,9 +6,10 @@ use winit::{ use winit::{ dpi::{LogicalSize, PhysicalSize}, - event::WindowEvent, + event::{WindowEvent, TouchPhase}, }; + pub struct WindowState { pub physical_size: PhysicalSize, pub logical_size: LogicalSize, @@ -91,6 +92,25 @@ impl WindowState { } => { self.right_mouse_btn = *state == ElementState::Pressed; } + WindowEvent::Touch(touch) => { + // Touch location is a PhysicalPosition + self.cursor_physical_position = touch.location; + self.cursor_logical_position = touch.location.to_logical(self.scale_factor); + + match touch.phase { + TouchPhase::Started => { + // Finger down -> treat like left button press + self.left_mouse_btn = true; + } + TouchPhase::Ended | TouchPhase::Cancelled => { + // Finger up/cancel -> treat like left button release + self.left_mouse_btn = false; + } + TouchPhase::Moved => { + // Just movement; button state unchanged + } + } + } _ => {} } } @@ -160,6 +180,9 @@ impl WinitEvent for WindowEvent { button, .. } => button == &btn, + Self::Touch(touch) => { + btn == MouseButton::Left && matches!(touch.phase, TouchPhase::Started) + } _ => false, } } @@ -171,6 +194,10 @@ impl WinitEvent for WindowEvent { button, .. } => button == &btn, + Self::Touch(touch) => { + btn == MouseButton::Left + && matches!(touch.phase, TouchPhase::Ended | TouchPhase::Cancelled) + } _ => false, } }