[PATCH 3/3] evdev: Add middle buttton scrolling for trackpoints

Hans de Goede hdegoede at redhat.com
Fri Sep 12 07:04:45 PDT 2014


Hi,

On 09/03/2014 05:57 AM, Peter Hutterer wrote:
> On Tue, Sep 02, 2014 at 04:34:50PM +0200, Hans de Goede wrote:
>> Most trackpoint users want to be able to scroll using the trackpoint with
>> the middle button pressed, add support for this.
>>
>> Signed-off-by: Hans de Goede <hdegoede at redhat.com>
> 
> yes, but I'd like to wait for dmitry to merge the INPUT_PROP_POINTING_STICK
> patch before we rely on it.

Understood, in the mean time this has been queued up for Linus :

https://git.kernel.org/cgit/linux/kernel/git/dtor/input.git/log/?h=for-linus

So we're good from that pov. Still please do not merge this yet,
I've asked a friend who is a long time trackpoint user to test
and the scrolling is much to quick atm (tested with xf86-input-libinput),
so this needs some work, for starters I'm going to take out the accel,
and see of that does the trick.




> 
>> ---
>>  include/linux/input.h |  1 +
>>  src/evdev.c           | 55 +++++++++++++++++++++++++++++++++++++++++++++++++++
>>  src/evdev.h           |  5 +++++
>>  3 files changed, 61 insertions(+)
>>
>> diff --git a/include/linux/input.h b/include/linux/input.h
>> index aa98ce7..39b550b 100644
>> --- a/include/linux/input.h
>> +++ b/include/linux/input.h
>> @@ -163,6 +163,7 @@ struct input_keymap_entry {
>>  #define INPUT_PROP_BUTTONPAD		0x02	/* has button(s) under pad */
>>  #define INPUT_PROP_SEMI_MT		0x03	/* touch rectangle only */
>>  #define INPUT_PROP_TOPBUTTONPAD		0x04	/* softbuttons at top of pad */
>> +#define INPUT_PROP_POINTING_STICK	0x05	/* is a pointing stick */
>>  
>>  #define INPUT_PROP_MAX			0x1f
>>  #define INPUT_PROP_CNT			(INPUT_PROP_MAX + 1)
>> diff --git a/src/evdev.c b/src/evdev.c
>> index b45f7ec..f013362 100644
>> --- a/src/evdev.c
>> +++ b/src/evdev.c
>> @@ -40,6 +40,7 @@
>>  #include "libinput-private.h"
>>  
>>  #define DEFAULT_AXIS_STEP_DISTANCE 10
>> +#define DEFAULT_MIDDLE_BUTTON_SCROLL_TIMEOUT 200
>>  
>>  enum evdev_key_type {
>>  	EVDEV_KEY_TYPE_NONE,
>> @@ -208,6 +209,14 @@ evdev_flush_pending_event(struct evdev_device *device, uint64_t time)
>>  		if (motion.dx == 0.0 && motion.dy == 0.0)
>>  			break;
>>  
>> +		if (device->scroll.middle_button_scroll &&
>> +		    is_key_down(device, BTN_MIDDLE)) {
>> +			if (device->scroll.middle_button_scroll_active)
>> +				evdev_post_scroll(device, time,
>> +						  motion.dx, motion.dy, 5.0);
>> +			break;
>> +		}
>> +
>>  		pointer_notify_motion(base, time, motion.dx, motion.dy);
>>  		break;
>>  	case EVDEV_ABSOLUTE_MT_DOWN:
>> @@ -345,6 +354,37 @@ get_key_type(uint16_t code)
>>  }
>>  
>>  static void
>> +evdev_middle_button_scroll_timeout(uint64_t time, void *data)
>> +{
>> +	struct evdev_device *device = data;
>> +
>> +	device->scroll.middle_button_scroll_active = true;
>> +}
>> +
>> +static void
>> +evdev_middle_button_scroll_button(struct evdev_device *device,
>> +				 uint64_t time, int value)
>> +{
>> +	if (value) {
>> +		libinput_timer_set(&device->scroll.timer,
>> +				time + DEFAULT_MIDDLE_BUTTON_SCROLL_TIMEOUT);
>> +	} else {
>> +		libinput_timer_cancel(&device->scroll.timer);
>> +		if (device->scroll.middle_button_scroll_active) {
>> +			evdev_stop_scroll(device, time);
>> +			device->scroll.middle_button_scroll_active = false;
>> +		} else {
>> +			/* If the button is released early enough emit the
> 
> s/early/quickly/

Fixed.

Regards,

Hans


> 
> Reviewed-by: Peter Hutterer <peter.hutterer at who-t.net>
> otherwise.
> 
> Cheers,
>    Peter
> 
> 
>> +			 * button press/release events. */
>> +			evdev_pointer_notify_button(device, time, BTN_MIDDLE,
>> +					LIBINPUT_BUTTON_STATE_PRESSED);
>> +			evdev_pointer_notify_button(device, time, BTN_MIDDLE,
>> +					LIBINPUT_BUTTON_STATE_RELEASED);
>> +		}
>> +	}
>> +}
>> +
>> +static void
>>  evdev_process_touch_button(struct evdev_device *device,
>>  			   uint64_t time, int value)
>>  {
>> @@ -404,6 +444,12 @@ evdev_process_key(struct evdev_device *device,
>>  				   LIBINPUT_KEY_STATE_RELEASED);
>>  		break;
>>  	case EVDEV_KEY_TYPE_BUTTON:
>> +		if (device->scroll.middle_button_scroll &&
>> +		    e->code == BTN_MIDDLE) {
>> +			evdev_middle_button_scroll_button(device, time,
>> +							  e->value);
>> +			break;
>> +		}
>>  		evdev_pointer_notify_button(
>>  			device,
>>  			time,
>> @@ -836,6 +882,15 @@ evdev_configure_device(struct evdev_device *device)
>>  			device->mt.slot = active_slot;
>>  		}
>>  	}
>> +
>> +	if (libevdev_has_property(evdev, INPUT_PROP_POINTING_STICK)) {
>> +		libinput_timer_init(&device->scroll.timer,
>> +				    device->base.seat->libinput,
>> +				    evdev_middle_button_scroll_timeout,
>> +				    device);
>> +		device->scroll.middle_button_scroll = true;
>> +	}
>> +
>>  	if (libevdev_has_event_code(evdev, EV_REL, REL_X) ||
>>  	    libevdev_has_event_code(evdev, EV_REL, REL_Y))
>>  		has_rel = 1;
>> diff --git a/src/evdev.h b/src/evdev.h
>> index 1cb6bea..2617b7f 100644
>> --- a/src/evdev.h
>> +++ b/src/evdev.h
>> @@ -26,10 +26,12 @@
>>  
>>  #include "config.h"
>>  
>> +#include <stdbool.h>
>>  #include "linux/input.h"
>>  #include <libevdev/libevdev.h>
>>  
>>  #include "libinput-private.h"
>> +#include "timer.h"
>>  
>>  enum evdev_event_type {
>>  	EVDEV_NONE,
>> @@ -90,6 +92,9 @@ struct evdev_device {
>>  	} rel;
>>  
>>  	struct {
>> +		struct libinput_timer timer;
>> +		bool middle_button_scroll;
>> +		bool middle_button_scroll_active;
>>  		int32_t direction;
>>  	} scroll;
>>  
>> -- 
>> 2.1.0


More information about the wayland-devel mailing list