diff --git a/src/config.c b/src/config.c index 05d5376..9cfdaa6 100644 --- a/src/config.c +++ b/src/config.c @@ -41,6 +41,7 @@ static struct { ARG_LAYER, ARG_LAYOUT, ARG_TIMEOUT, + ARG_SENSITIVITY, ARG_DESCRIPTOR, } args[MAX_DESCRIPTOR_ARGS]; } actions[] = { @@ -66,7 +67,11 @@ static struct { { "macro2", NULL, OP_MACRO2, { ARG_TIMEOUT, ARG_TIMEOUT, ARG_MACRO } }, { "setlayout", NULL, OP_LAYOUT, { ARG_LAYOUT } }, - //TODO: deprecate + /* Experimental */ + { "scrollt", NULL, OP_SCROLL_TOGGLE, {ARG_SENSITIVITY} }, + { "scroll", NULL, OP_SCROLL, {ARG_SENSITIVITY} }, + + /* TODO: deprecate */ { "overload2", "overloadt", OP_OVERLOAD_TIMEOUT, { ARG_LAYER, ARG_DESCRIPTOR, ARG_TIMEOUT } }, { "overload3", "overloadt2", OP_OVERLOAD_TIMEOUT_TAP, { ARG_LAYER, ARG_DESCRIPTOR, ARG_TIMEOUT } }, { "toggle2", "togglem", OP_TOGGLEM, { ARG_LAYER, ARG_MACRO } }, @@ -687,6 +692,9 @@ static int parse_descriptor(char *s, config->descriptors[config->nr_descriptors] = desc; arg->idx = config->nr_descriptors++; break; + case ARG_SENSITIVITY: + arg->sensitivity = atoi(argstr); + break; case ARG_TIMEOUT: arg->timeout = atoi(argstr); break; diff --git a/src/config.h b/src/config.h index b7c5271..a68c3ad 100644 --- a/src/config.h +++ b/src/config.h @@ -45,7 +45,11 @@ enum op { OP_MACRO, OP_MACRO2, OP_COMMAND, - OP_TIMEOUT + OP_TIMEOUT, + +/* Experimental */ + OP_SCROLL_TOGGLE, + OP_SCROLL, }; union descriptor_arg { @@ -54,6 +58,7 @@ union descriptor_arg { int16_t idx; uint16_t sz; uint16_t timeout; + int16_t sensitivity; }; /* Describes the intended purpose of a key (corresponds to an 'action' in user parlance). */ diff --git a/src/daemon.c b/src/daemon.c index a2d8748..53aee30 100644 --- a/src/daemon.c +++ b/src/daemon.c @@ -417,6 +417,7 @@ static int event_handler(struct event *ev) break; case EV_DEV_EVENT: if (ev->dev->data) { + struct keyboard *kbd = ev->dev->data; timeout_kbd = ev->dev->data; switch (ev->devev->type) { case DEV_KEY: @@ -426,10 +427,28 @@ static int event_handler(struct event *ev) kev.pressed = ev->devev->pressed; kev.timestamp = ev->timestamp; - timeout = kbd_process_events(ev->dev->data, &kev, 1); + timeout = kbd_process_events(kbd, &kev, 1); break; case DEV_MOUSE_MOVE: - vkbd_mouse_move(vkbd, ev->devev->x, ev->devev->y); + if (kbd->scroll.active) { + if (kbd->scroll.sensitivity == 0) + break; + int xticks, yticks; + + kbd->scroll.y += ev->devev->y; + kbd->scroll.x += ev->devev->x; + + yticks = kbd->scroll.y / kbd->scroll.sensitivity; + kbd->scroll.y %= kbd->scroll.sensitivity; + + xticks = kbd->scroll.x / kbd->scroll.sensitivity; + kbd->scroll.x %= kbd->scroll.sensitivity; + + vkbd_mouse_scroll(vkbd, 0, -1*yticks); + vkbd_mouse_scroll(vkbd, 0, xticks); + } else { + vkbd_mouse_move(vkbd, ev->devev->x, ev->devev->y); + } break; case DEV_MOUSE_MOVE_ABS: vkbd_mouse_move_abs(vkbd, ev->devev->x, ev->devev->y); diff --git a/src/keyboard.c b/src/keyboard.c index e2b9b8f..cf24ef3 100644 --- a/src/keyboard.c +++ b/src/keyboard.c @@ -520,6 +520,18 @@ static long process_descriptor(struct keyboard *kbd, uint8_t code, } break; + case OP_SCROLL: + kbd->scroll.sensitivity = d->args[0].sensitivity; + if (pressed) + kbd->scroll.active = 1; + else + kbd->scroll.active = 0; + break; + case OP_SCROLL_TOGGLE: + kbd->scroll.sensitivity = d->args[0].sensitivity; + if (pressed) + kbd->scroll.active = !kbd->scroll.active; + break; case OP_OVERLOAD_TIMEOUT_TAP: case OP_OVERLOAD_TIMEOUT: if (pressed) { diff --git a/src/keyboard.h b/src/keyboard.h index 7a50b11..5159545 100644 --- a/src/keyboard.h +++ b/src/keyboard.h @@ -115,6 +115,14 @@ struct keyboard { uint8_t keystate[256]; void (*output) (uint8_t code, uint8_t state); void (*layer_observer) (struct keyboard *kbd, const char *layer, int state); + + struct { + int x; + int y; + + int sensitivity; /* Mouse units per scroll unit (higher == slower scrolling). */ + int active; + } scroll; }; struct keyboard *new_keyboard(struct config *config,