Remove XInput2 code for handling keyboard events

* For the moment we're still using plain core X11 events
   for handling keyboard activity, so remove the XInput2 code for that

 * Small refactoring of X11 input handling and documentation fixes
This commit is contained in:
Robert Knight 2015-06-28 21:55:54 +01:00
parent 94c31e42a4
commit cb08d9b05b
2 changed files with 35 additions and 58 deletions

View file

@ -13,8 +13,7 @@ use super::XConnection;
#[derive(Debug)] #[derive(Debug)]
enum AxisType { enum AxisType {
HorizontalScroll, HorizontalScroll,
VerticalScroll, VerticalScroll
Other
} }
#[derive(Debug)] #[derive(Debug)]
@ -33,7 +32,11 @@ struct AxisValue {
} }
struct InputState { struct InputState {
/// Last-seen cursor position within a window in (x, y)
/// coordinates
cursor_pos: (f64, f64), cursor_pos: (f64, f64),
/// Last-seen positions of axes, used to report delta
/// movements when a new absolute axis value is received
axis_values: Vec<AxisValue> axis_values: Vec<AxisValue>
} }
@ -68,7 +71,10 @@ impl XInputEventHandler {
} }
} }
// specify the XInput events we want to receive // specify the XInput events we want to receive.
// Button clicks and mouse events are handled via XInput
// events. Key presses are still handled via plain core
// X11 events.
let mut mask: [libc::c_uchar; 1] = [0]; let mut mask: [libc::c_uchar; 1] = [0];
let mut input_event_mask = ffi::XIEventMask { let mut input_event_mask = ffi::XIEventMask {
deviceid: ffi::XIAllDevices, deviceid: ffi::XIAllDevices,
@ -132,10 +138,8 @@ impl XInputEventHandler {
str::from_utf8(&buffer[..count as usize]).unwrap_or("").to_string() str::from_utf8(&buffer[..count as usize]).unwrap_or("").to_string()
}; };
{ for chr in written.chars() {
for chr in written.chars() { translated_events.push(ReceivedCharacter(chr));
translated_events.push(ReceivedCharacter(chr));
}
} }
let mut keysym = unsafe { let mut keysym = unsafe {
@ -159,19 +163,6 @@ impl XInputEventHandler {
use events::MouseScrollDelta::{PixelDelta, LineDelta}; use events::MouseScrollDelta::{PixelDelta, LineDelta};
match cookie.evtype { match cookie.evtype {
ffi::XI_KeyPress | ffi::XI_KeyRelease => {
let event_data: &ffi::XIDeviceEvent = unsafe{mem::transmute(cookie.data)};
if cookie.evtype == ffi::XI_KeyPress {
if event_data.flags & ffi::XIKeyRepeat == 0 {
println!("XInput Key {} pressed", event_data.detail);
None
} else {
None
}
} else {
None
}
},
ffi::XI_ButtonPress | ffi::XI_ButtonRelease => { ffi::XI_ButtonPress | ffi::XI_ButtonRelease => {
let event_data: &ffi::XIDeviceEvent = unsafe{mem::transmute(cookie.data)}; let event_data: &ffi::XIDeviceEvent = unsafe{mem::transmute(cookie.data)};
let state = if cookie.evtype == ffi::XI_ButtonPress { let state = if cookie.evtype == ffi::XI_ButtonPress {
@ -183,23 +174,23 @@ impl XInputEventHandler {
ffi::Button1 => Some(MouseInput(state, Left)), ffi::Button1 => Some(MouseInput(state, Left)),
ffi::Button2 => Some(MouseInput(state, Middle)), ffi::Button2 => Some(MouseInput(state, Middle)),
ffi::Button3 => Some(MouseInput(state, Right)), ffi::Button3 => Some(MouseInput(state, Right)),
ffi::Button4 => { ffi::Button4 | ffi::Button5 => {
if event_data.flags & ffi::XIPointerEmulated == 0 { if event_data.flags & ffi::XIPointerEmulated == 0 {
Some(MouseWheel(LineDelta(0.0, 1.0))) // scroll event from a traditional wheel with
// distinct 'clicks'
let delta = if event_data.detail as u32 == ffi::Button4 {
1.0
} else {
-1.0
};
Some(MouseWheel(LineDelta(0.0, delta)))
} else { } else {
// emulated button event from a touch/smooth-scroll // emulated button event from a touch/smooth-scroll
// event. Scrolling is instead reported via the // event. Ignore these events and handle scrolling
// XI_Motion event handler // via XI_Motion event handler instead
None None
} }
}, }
ffi::Button5 => {
if event_data.flags & ffi::XIPointerEmulated == 0 {
Some(MouseWheel(LineDelta(0.0, -1.0)))
} else {
None
}
},
_ => None _ => None
} }
}, },
@ -252,6 +243,9 @@ fn read_input_axis_info(display: &Arc<XConnection>) -> Vec<Axis> {
for k in 0..device.num_classes { for k in 0..device.num_classes {
let class = unsafe { *(device.classes.offset(k as isize)) }; let class = unsafe { *(device.classes.offset(k as isize)) };
match unsafe { (*class)._type } { match unsafe { (*class)._type } {
// Note that scroll axis
// are reported both as 'XIScrollClass' and 'XIValuatorClass'
// axes. For the moment we only care about scrolling axes.
ffi::XIScrollClass => { ffi::XIScrollClass => {
let scroll_class: &ffi::XIScrollClassInfo = unsafe{mem::transmute(class)}; let scroll_class: &ffi::XIScrollClassInfo = unsafe{mem::transmute(class)};
axis_list.push(Axis{ axis_list.push(Axis{
@ -265,34 +259,16 @@ fn read_input_axis_info(display: &Arc<XConnection>) -> Vec<Axis> {
} }
}) })
}, },
ffi::XIValuatorClass => {
let valuator_class: &ffi::XIValuatorClassInfo = unsafe{mem::transmute(class)};
axis_list.push(Axis{
id: valuator_class.sourceid,
device_id: device.deviceid,
axis_number: valuator_class.number,
axis_type: AxisType::Other
})
},
_ => {} _ => {}
} }
} }
} }
axis_list.sort_by(|a, b| {
if a.device_id != b.device_id {
a.device_id.cmp(&b.device_id)
} else if a.id != b.id {
a.id.cmp(&b.id)
} else {
a.axis_number.cmp(&b.axis_number)
}
});
axis_list axis_list
} }
/// Given an input motion event for an axis and the previous /// Given an input motion event for an axis and the previous
/// state of the axises, return the horizontal/vertical /// state of the axes, return the horizontal/vertical
/// scroll deltas /// scroll deltas
fn calc_scroll_deltas(event: &ffi::XIDeviceEvent, fn calc_scroll_deltas(event: &ffi::XIDeviceEvent,
axis_id: i32, axis_id: i32,
@ -326,8 +302,7 @@ fn calc_scroll_deltas(event: &ffi::XIDeviceEvent,
axis.axis_number == axis_id { axis.axis_number == axis_id {
match axis.axis_type { match axis.axis_type {
AxisType::HorizontalScroll => scroll_delta.0 = delta, AxisType::HorizontalScroll => scroll_delta.0 = delta,
AxisType::VerticalScroll => scroll_delta.1 = delta, AxisType::VerticalScroll => scroll_delta.1 = delta
_ => {}
} }
} }
} }

View file

@ -177,15 +177,17 @@ impl<'a> Iterator for PollEventsIterator<'a> {
return Some(ev); return Some(ev);
} }
let xlib = &self.window.x.display.xlib;
loop { loop {
let mut xev = unsafe { mem::uninitialized() }; let mut xev = unsafe { mem::uninitialized() };
let res = unsafe { (self.window.x.display.xlib.XCheckMaskEvent)(self.window.x.display.display, -1, &mut xev) }; let res = unsafe { (xlib.XCheckMaskEvent)(self.window.x.display.display, -1, &mut xev) };
if res == 0 { if res == 0 {
let res = unsafe { (self.window.x.display.xlib.XCheckTypedEvent)(self.window.x.display.display, ffi::ClientMessage, &mut xev) }; let res = unsafe { (xlib.XCheckTypedEvent)(self.window.x.display.display, ffi::ClientMessage, &mut xev) };
if res == 0 { if res == 0 {
let res = unsafe { (self.window.x.display.xlib.XCheckTypedEvent)(self.window.x.display.display, ffi::GenericEvent, &mut xev) }; let res = unsafe { (xlib.XCheckTypedEvent)(self.window.x.display.display, ffi::GenericEvent, &mut xev) };
if res == 0 { if res == 0 {
return None; return None;
} }
@ -194,7 +196,7 @@ impl<'a> Iterator for PollEventsIterator<'a> {
match xev.get_type() { match xev.get_type() {
ffi::KeymapNotify => { ffi::KeymapNotify => {
unsafe { (self.window.x.display.xlib.XRefreshKeyboardMapping)(mem::transmute(&xev)); } unsafe { (xlib.XRefreshKeyboardMapping)(mem::transmute(&xev)); }
}, },
ffi::ClientMessage => { ffi::ClientMessage => {