109 lines
2.8 KiB
Rust
109 lines
2.8 KiB
Rust
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
|
|
pub enum MouseButton {
|
|
Left,
|
|
Right,
|
|
Middle,
|
|
}
|
|
|
|
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
|
|
pub enum MouseEventType {
|
|
Down(MouseButton),
|
|
Up(MouseButton),
|
|
Move,
|
|
}
|
|
|
|
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
|
|
pub struct MouseEvent {
|
|
pub etype: MouseEventType,
|
|
pub pos: (u32, u32),
|
|
}
|
|
|
|
#[derive(Copy, Clone, Default, PartialEq, Eq)]
|
|
pub struct MouseState {
|
|
pub buttons: [bool; 3],
|
|
pub pos: (u32, u32),
|
|
}
|
|
|
|
impl MouseEvent {
|
|
pub fn new(etype: MouseEventType, pos: (u32, u32)) -> Self {
|
|
Self {
|
|
etype,
|
|
pos,
|
|
}
|
|
}
|
|
}
|
|
|
|
impl From<usize> for MouseButton {
|
|
fn from(index: usize) -> MouseButton {
|
|
match index {
|
|
0 => MouseButton::Left,
|
|
1 => MouseButton::Right,
|
|
2 => MouseButton::Middle,
|
|
_ => panic!("unexpected mouse button index: {:?}", index),
|
|
}
|
|
}
|
|
}
|
|
|
|
impl From<MouseButton> for usize {
|
|
fn from(button: MouseButton) -> usize {
|
|
match button {
|
|
MouseButton::Left => 0,
|
|
MouseButton::Right => 1,
|
|
MouseButton::Middle => 2,
|
|
}
|
|
}
|
|
}
|
|
|
|
impl MouseState {
|
|
pub fn with(left: bool, right: bool, middle: bool, x: u32, y: u32) -> Self {
|
|
Self {
|
|
buttons: [left, right, middle],
|
|
pos: (x, y),
|
|
}
|
|
}
|
|
|
|
pub fn to_events(&mut self, next_state: MouseState) -> Vec<MouseEvent> {
|
|
if *self != next_state {
|
|
self.pos = next_state.pos;
|
|
|
|
let events: Vec<MouseEvent> = self
|
|
.buttons
|
|
.into_iter()
|
|
.zip(next_state.buttons)
|
|
.enumerate()
|
|
.filter_map(|(i, (prev, next))| {
|
|
if prev != next {
|
|
self.buttons[i] = next;
|
|
let button = MouseButton::from(i);
|
|
let etype = if next {
|
|
MouseEventType::Down(button)
|
|
} else {
|
|
MouseEventType::Up(button)
|
|
};
|
|
Some(MouseEvent::new(etype, next_state.pos))
|
|
} else {
|
|
None
|
|
}
|
|
})
|
|
.collect();
|
|
|
|
if !events.is_empty() {
|
|
events
|
|
} else {
|
|
vec![MouseEvent::new(MouseEventType::Move, next_state.pos)]
|
|
}
|
|
} else {
|
|
vec![]
|
|
}
|
|
}
|
|
|
|
pub fn update_with(&mut self, event: MouseEvent) {
|
|
self.pos = event.pos;
|
|
match event.etype {
|
|
MouseEventType::Up(button) => self.buttons[usize::from(button)] = false,
|
|
MouseEventType::Down(button) => self.buttons[usize::from(button)] = true,
|
|
MouseEventType::Move => {},
|
|
}
|
|
}
|
|
}
|