From 54b00fd7ddff80e34dfb3d24702939918e1d939f Mon Sep 17 00:00:00 2001 From: MURAOKA Taro Date: Sat, 2 Apr 2022 12:29:15 +0900 Subject: [PATCH] scroll snap feature introduce scroll snap feature. scroll snap locks an axis to scroll at first, then unlock it if ball moved to another axis an amount. apply clang-format. configuration for clang-format is changed in QMK. this apply it on files exclude config.h files. --- .../keyball/drivers/pmw3360/pmw3360.c | 14 ++-- .../keyball/drivers/pmw3360/pmw3360.h | 14 ++-- .../keyball39/keymaps/default/keymap.c | 2 +- .../keyball39/keymaps/develop/keymap.c | 2 +- .../keyball/keyball39/keymaps/via/keymap.c | 2 +- .../keyboards/keyball/keyball46/keyball46.c | 4 +- .../keyball61/keymaps/develop/keymap.c | 2 +- .../keyball/keyball61/keymaps/via/keymap.c | 2 +- .../keyboards/keyball/keyball61/matrix.c | 22 +++--- .../keyboards/keyball/lib/keyball/keyball.c | 68 +++++++++++++++---- .../keyboards/keyball/lib/keyball/keyball.h | 45 ++++++++---- .../keyboards/keyball/lib/oledkit/oledkit.c | 14 ++-- .../keyboards/keyball/lib/oledkit/oledkit.h | 2 +- 13 files changed, 135 insertions(+), 58 deletions(-) diff --git a/qmk_firmware/keyboards/keyball/drivers/pmw3360/pmw3360.c b/qmk_firmware/keyboards/keyball/drivers/pmw3360/pmw3360.c index 1507c880d..d2127b0f1 100644 --- a/qmk_firmware/keyboards/keyball/drivers/pmw3360/pmw3360.c +++ b/qmk_firmware/keyboards/keyball/drivers/pmw3360/pmw3360.c @@ -22,7 +22,9 @@ along with this program. If not, see . #define PMW3360_SPI_DIVISOR (F_CPU / PMW3360_CLOCKS) #define PMW3360_CLOCKS 70000000 -bool pmw3360_spi_start(void) { return spi_start(PMW3360_NCS_PIN, false, PMW3360_SPI_MODE, PMW3360_SPI_DIVISOR); } +bool pmw3360_spi_start(void) { + return spi_start(PMW3360_NCS_PIN, false, PMW3360_SPI_MODE, PMW3360_SPI_DIVISOR); +} uint8_t pmw3360_reg_read(uint8_t addr) { pmw3360_spi_start(); @@ -42,7 +44,9 @@ void pmw3360_reg_write(uint8_t addr, uint8_t data) { wait_us(180); } -uint8_t pmw3360_cpi_get(void) { return pmw3360_reg_read(pmw3360_Config1); } +uint8_t pmw3360_cpi_get(void) { + return pmw3360_reg_read(pmw3360_Config1); +} void pmw3360_cpi_set(uint8_t cpi) { if (cpi > pmw3360_MAXCPI) { @@ -68,7 +72,9 @@ void pmw3360_scan_perf_task(void) { } } -uint32_t pmw3360_scan_rate_get(void) { return pmw3360_last_count; } +uint32_t pmw3360_scan_rate_get(void) { + return pmw3360_last_count; +} bool pmw3360_motion_read(pmw3360_motion_t *d) { #ifdef DEBUG_PMW3360_SCAN_RATE @@ -97,7 +103,7 @@ bool pmw3360_motion_burst(pmw3360_motion_t *d) { spi_stop(); return false; } - spi_read(); // skip Observation + spi_read(); // skip Observation d->x = spi_read(); d->x |= spi_read() << 8; d->y = spi_read(); diff --git a/qmk_firmware/keyboards/keyball/drivers/pmw3360/pmw3360.h b/qmk_firmware/keyboards/keyball/drivers/pmw3360/pmw3360.h index 044123ccc..0f6b236d0 100644 --- a/qmk_firmware/keyboards/keyball/drivers/pmw3360/pmw3360.h +++ b/qmk_firmware/keyboards/keyball/drivers/pmw3360/pmw3360.h @@ -127,7 +127,7 @@ typedef enum { } pmw3360_reg_t; enum { - pmw3360_MAXCPI = 0x77, // = 119: 12000 CPI + pmw3360_MAXCPI = 0x77, // = 119: 12000 CPI }; ////////////////////////////////////////////////////////////////////////////// @@ -135,8 +135,14 @@ enum { bool pmw3360_spi_start(void); -void inline pmw3360_spi_stop(void) { spi_stop(); } +void inline pmw3360_spi_stop(void) { + spi_stop(); +} -spi_status_t inline pmw3360_spi_write(uint8_t data) { return spi_write(data); } +spi_status_t inline pmw3360_spi_write(uint8_t data) { + return spi_write(data); +} -spi_status_t inline pmw3360_spi_read(void) { return spi_read(); } +spi_status_t inline pmw3360_spi_read(void) { + return spi_read(); +} diff --git a/qmk_firmware/keyboards/keyball/keyball39/keymaps/default/keymap.c b/qmk_firmware/keyboards/keyball/keyball39/keymaps/default/keymap.c index 6ccbc5b0e..4a6e4a187 100644 --- a/qmk_firmware/keyboards/keyball/keyball39/keymaps/default/keymap.c +++ b/qmk_firmware/keyboards/keyball/keyball39/keymaps/default/keymap.c @@ -61,7 +61,7 @@ layer_state_t layer_state_set_user(layer_state_t state) { #ifdef OLED_ENABLE -#include "lib/oledkit/oledkit.h" +# include "lib/oledkit/oledkit.h" void oledkit_render_info_user(void) { keyball_oled_render_keyinfo(); diff --git a/qmk_firmware/keyboards/keyball/keyball39/keymaps/develop/keymap.c b/qmk_firmware/keyboards/keyball/keyball39/keymaps/develop/keymap.c index 40e34c53c..1d943c7b0 100644 --- a/qmk_firmware/keyboards/keyball/keyball39/keymaps/develop/keymap.c +++ b/qmk_firmware/keyboards/keyball/keyball39/keymaps/develop/keymap.c @@ -41,7 +41,7 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { #ifdef OLED_ENABLE -#include "lib/oledkit/oledkit.h" +# include "lib/oledkit/oledkit.h" void oledkit_render_info_user(void) { keyball_oled_render_keyinfo(); diff --git a/qmk_firmware/keyboards/keyball/keyball39/keymaps/via/keymap.c b/qmk_firmware/keyboards/keyball/keyball39/keymaps/via/keymap.c index 3d4f02688..785372c20 100644 --- a/qmk_firmware/keyboards/keyball/keyball39/keymaps/via/keymap.c +++ b/qmk_firmware/keyboards/keyball/keyball39/keymaps/via/keymap.c @@ -61,7 +61,7 @@ layer_state_t layer_state_set_user(layer_state_t state) { #ifdef OLED_ENABLE -#include "lib/oledkit/oledkit.h" +# include "lib/oledkit/oledkit.h" void oledkit_render_info_user(void) { keyball_oled_render_keyinfo(); diff --git a/qmk_firmware/keyboards/keyball/keyball46/keyball46.c b/qmk_firmware/keyboards/keyball/keyball46/keyball46.c index fbd003655..14283834c 100644 --- a/qmk_firmware/keyboards/keyball/keyball46/keyball46.c +++ b/qmk_firmware/keyboards/keyball/keyball46/keyball46.c @@ -51,7 +51,7 @@ static uint8_t peek_matrix_intersection(pin_t out_pin, pin_t in_pin) { } bool is_keyboard_left(void) { - return !peek_matrix_intersection(keyball.this_have_ball ? F7: F6, B5); + return !peek_matrix_intersection(keyball.this_have_ball ? F7 : F6, B5); } ////////////////////////////////////////////////////////////////////////////// @@ -59,7 +59,7 @@ bool is_keyboard_left(void) { void keyball_on_adjust_layout(keyball_adjust_t v) { if (v == KEYBALL_ADJUST_PRIMARY) { // adjust matrix mask - bool is_left = is_keyboard_left(); + bool is_left = is_keyboard_left(); matrix_mask[(is_left ? 2 : 6) + (keyball.this_have_ball ? 0 : 1)] = 0b0111111; matrix_mask[(is_left ? 6 : 2) + (keyball.that_have_ball ? 0 : 1)] = 0b0111111; } diff --git a/qmk_firmware/keyboards/keyball/keyball61/keymaps/develop/keymap.c b/qmk_firmware/keyboards/keyball/keyball61/keymaps/develop/keymap.c index 96da86f63..bcf50be7b 100644 --- a/qmk_firmware/keyboards/keyball/keyball61/keymaps/develop/keymap.c +++ b/qmk_firmware/keyboards/keyball/keyball61/keymaps/develop/keymap.c @@ -49,7 +49,7 @@ void keyboard_post_init_user(void) { #ifdef OLED_ENABLE -#include "lib/oledkit/oledkit.h" +# include "lib/oledkit/oledkit.h" void oledkit_render_info_user(void) { keyball_oled_render_keyinfo(); diff --git a/qmk_firmware/keyboards/keyball/keyball61/keymaps/via/keymap.c b/qmk_firmware/keyboards/keyball/keyball61/keymaps/via/keymap.c index ada95419a..cb923bcbd 100644 --- a/qmk_firmware/keyboards/keyball/keyball61/keymaps/via/keymap.c +++ b/qmk_firmware/keyboards/keyball/keyball61/keymaps/via/keymap.c @@ -64,7 +64,7 @@ layer_state_t layer_state_set_user(layer_state_t state) { #ifdef OLED_ENABLE -#include "lib/oledkit/oledkit.h" +# include "lib/oledkit/oledkit.h" void oledkit_render_info_user(void) { keyball_oled_render_keyinfo(); diff --git a/qmk_firmware/keyboards/keyball/keyball61/matrix.c b/qmk_firmware/keyboards/keyball/keyball61/matrix.c index 79945a200..fff1d2662 100644 --- a/qmk_firmware/keyboards/keyball/keyball61/matrix.c +++ b/qmk_firmware/keyboards/keyball/keyball61/matrix.c @@ -22,11 +22,11 @@ along with this program. If not, see . #include "split_common/split_util.h" #include "split_common/transactions.h" -#define PINNUM_ROW (MATRIX_ROWS / 2) -#define PINNUM_COL (MATRIX_COLS / 2) +#define PINNUM_ROW (MATRIX_ROWS / 2) +#define PINNUM_COL (MATRIX_COLS / 2) -#define ROWS_PER_HAND (MATRIX_ROWS / 2) -#define MATRIXSIZE_PER_HAND (ROWS_PER_HAND * sizeof(matrix_row_t)) +#define ROWS_PER_HAND (MATRIX_ROWS / 2) +#define MATRIXSIZE_PER_HAND (ROWS_PER_HAND * sizeof(matrix_row_t)) static pin_t row_pins[PINNUM_ROW] = MATRIX_ROW_PINS; static pin_t col_pins[PINNUM_COL] = MATRIX_COL_PINS; @@ -61,7 +61,7 @@ static bool duplex_scan(matrix_row_t current_matrix[]) { for (uint8_t col = 0; col < PINNUM_COL; col++) { bool on = !get_pin(col_pins[col]); if (on) { - next |= 1 << col; + next |= 1 << col; } else { next &= ~(1 << col); } @@ -70,7 +70,7 @@ static bool duplex_scan(matrix_row_t current_matrix[]) { matrix_output_unselect_delay(row, next != 0); if (current_matrix[row] != next) { current_matrix[row] = next; - changed = true; + changed = true; } } @@ -81,7 +81,7 @@ static bool duplex_scan(matrix_row_t current_matrix[]) { matrix_output_select_delay(); matrix_row_t shifter = ((matrix_row_t)1) << (col + PINNUM_COL); for (uint8_t row = 0; row < PINNUM_ROW; row++) { - bool on = !get_pin(row_pins[row]); + bool on = !get_pin(row_pins[row]); matrix_row_t prev = current_matrix[row]; if (on) { current_matrix[row] |= shifter; @@ -115,7 +115,9 @@ void matrix_init_custom(void) { } // user-defined overridable functions -__attribute__((weak)) void matrix_slave_scan_kb(void) { matrix_slave_scan_user(); } +__attribute__((weak)) void matrix_slave_scan_kb(void) { + matrix_slave_scan_user(); +} __attribute__((weak)) void matrix_slave_scan_user(void) {} // override quantum/matrix_common.c @@ -135,8 +137,8 @@ uint8_t matrix_scan(void) { } // receive from secondary. - static bool last_connected = false; - matrix_row_t *that_raw = raw_matrix + ROWS_PER_HAND; + static bool last_connected = false; + matrix_row_t* that_raw = raw_matrix + ROWS_PER_HAND; memset(that_raw, 0, MATRIXSIZE_PER_HAND); if (transport_master_if_connected(matrix + thisHand, that_raw)) { last_connected = true; diff --git a/qmk_firmware/keyboards/keyball/lib/keyball/keyball.c b/qmk_firmware/keyboards/keyball/lib/keyball/keyball.c index 8feb7987d..d489c6ebd 100644 --- a/qmk_firmware/keyboards/keyball/lib/keyball/keyball.c +++ b/qmk_firmware/keyboards/keyball/lib/keyball/keyball.c @@ -60,10 +60,12 @@ static int16_t add16(int16_t a, int16_t b) { } // clip2int8 clips an integer fit into int8_t. -static inline int8_t clip2int8(int16_t v) { return (v) < -127 ? -127 : (v) > 127 ? 127 : (int8_t)v; } +static inline int8_t clip2int8(int16_t v) { + return (v) < -127 ? -127 : (v) > 127 ? 127 : (int8_t)v; +} static const char *format_4d(int8_t d) { - static char buf[5] = {0}; // max width (4) + NUL (1) + static char buf[5] = {0}; // max width (4) + NUL (1) char lead = ' '; if (d < 0) { d = -d; @@ -124,9 +126,13 @@ void pointing_device_driver_init(void) { } } -uint16_t pointing_device_driver_get_cpi(void) { return keyball_get_cpi(); } +uint16_t pointing_device_driver_get_cpi(void) { + return keyball_get_cpi(); +} -void pointing_device_driver_set_cpi(uint16_t cpi) { keyball_set_cpi(cpi); } +void pointing_device_driver_set_cpi(uint16_t cpi) { + keyball_set_cpi(cpi); +} static void motion_to_mouse_move(keyball_motion_t *m, report_mouse_t *r, bool is_left) { #if KEYBALL_MODEL == 61 || KEYBALL_MODEL == 39 @@ -147,16 +153,42 @@ static void motion_to_mouse_move(keyball_motion_t *m, report_mouse_t *r, bool is m->y = 0; } +static inline int16_t abs16(int16_t v) { + return v < 0 ? -v : v; +} + static void motion_to_mouse_scroll(keyball_motion_t *m, report_mouse_t *r, bool is_left) { + // consume motion of trackball. uint8_t div = keyball_get_scroll_div() - 1; int16_t x = m->x >> div; m->x -= x << div; int16_t y = m->y >> div; m->y -= y << div; + +#if KEYBALL_SCROLLSNAP_ENABLE + // scroll snap. + uint32_t now = timer_read32(); + if (x != 0 || y != 0) { + keyball.scroll_snap_last = now; + } else if (TIMER_DIFF_32(now, keyball.scroll_snap_last) >= KEYBALL_SCROLLSNAP_RESET_TIMER) { + keyball.scroll_snap_tension.x = 0; + keyball.scroll_snap_tension.y = 0; + } + if (abs16(keyball.scroll_snap_tension.x) < KEYBALL_SCROLLSNAP_TENSION_THRESHOLD) { + keyball.scroll_snap_tension.x += x; + x = 0; + } + if (abs16(keyball.scroll_snap_tension.y) < KEYBALL_SCROLLSNAP_TENSION_THRESHOLD) { + keyball.scroll_snap_tension.y += y; + y = 0; + } +#endif + + // apply to mouse report. #if KEYBALL_MODEL == 61 || KEYBALL_MODEL == 39 r->h = clip2int8(y); - r->v = clip2int8(x); - if (!is_left) { + r->v = -clip2int8(x); + if (is_left) { r->h = -r->h; r->v = -r->v; } @@ -187,7 +219,7 @@ static inline bool should_report(void) { last = now; #endif #if defined(KEYBALL_SCROLLBALL_INHIVITOR) && KEYBALL_SCROLLBALL_INHIVITOR > 0 - if (TIMER_DIFF_32(now, keyball.scroll_changed) < KEYBALL_SCROLLBALL_INHIVITOR) { + if (TIMER_DIFF_32(now, keyball.scroll_mode_changed) < KEYBALL_SCROLLBALL_INHIVITOR) { keyball.this_motion.x = 0; keyball.this_motion.y = 0; keyball.that_motion.x = 0; @@ -289,7 +321,9 @@ static void rpc_get_motion_invoke(void) { return; } -static void rpc_set_cpi_handler(uint8_t in_buflen, const void *in_data, uint8_t out_buflen, void *out_data) { keyball_set_cpi(*(keyball_cpi_t *)in_data); } +static void rpc_set_cpi_handler(uint8_t in_buflen, const void *in_data, uint8_t out_buflen, void *out_data) { + keyball_set_cpi(*(keyball_cpi_t *)in_data); +} static void rpc_set_cpi_invoke(void) { if (!keyball.cpi_changed) { @@ -379,20 +413,28 @@ void keyball_oled_render_keyinfo(void) { ////////////////////////////////////////////////////////////////////////////// // Public API functions -bool keyball_get_scroll_mode(void) { return keyball.scroll_mode; } +bool keyball_get_scroll_mode(void) { + return keyball.scroll_mode; +} void keyball_set_scroll_mode(bool mode) { if (mode != keyball.scroll_mode) { - keyball.scroll_changed = timer_read32(); + keyball.scroll_mode_changed = timer_read32(); } keyball.scroll_mode = mode; } -uint8_t keyball_get_scroll_div(void) { return keyball.scroll_div == 0 ? KEYBALL_SCROLL_DIV_DEFAULT : keyball.scroll_div; } +uint8_t keyball_get_scroll_div(void) { + return keyball.scroll_div == 0 ? KEYBALL_SCROLL_DIV_DEFAULT : keyball.scroll_div; +} -void keyball_set_scroll_div(uint8_t div) { keyball.scroll_div = div > SCROLL_DIV_MAX ? SCROLL_DIV_MAX : div; } +void keyball_set_scroll_div(uint8_t div) { + keyball.scroll_div = div > SCROLL_DIV_MAX ? SCROLL_DIV_MAX : div; +} -uint8_t keyball_get_cpi(void) { return keyball.cpi_value == 0 ? CPI_DEFAULT : keyball.cpi_value; } +uint8_t keyball_get_cpi(void) { + return keyball.cpi_value == 0 ? CPI_DEFAULT : keyball.cpi_value; +} void keyball_set_cpi(uint8_t cpi) { if (cpi > CPI_MAX) { diff --git a/qmk_firmware/keyboards/keyball/lib/keyball/keyball.h b/qmk_firmware/keyboards/keyball/lib/keyball/keyball.h index b320323d2..25ced3ddf 100644 --- a/qmk_firmware/keyboards/keyball/lib/keyball/keyball.h +++ b/qmk_firmware/keyboards/keyball/lib/keyball/keyball.h @@ -25,17 +25,29 @@ along with this program. If not, see . #endif #ifndef KEYBALL_SCROLL_DIV_DEFAULT -# define KEYBALL_SCROLL_DIV_DEFAULT 4 // 4: 1/8 (1/2^(n-1)) +# define KEYBALL_SCROLL_DIV_DEFAULT 4 // 4: 1/8 (1/2^(n-1)) #endif #ifndef KEYBALL_REPORTMOUSE_INTERVAL -# define KEYBALL_REPORTMOUSE_INTERVAL 8 // mouse report rate: 125Hz +# define KEYBALL_REPORTMOUSE_INTERVAL 8 // mouse report rate: 125Hz #endif #ifndef KEYBALL_SCROLLBALL_INHIVITOR # define KEYBALL_SCROLLBALL_INHIVITOR 50 #endif +#ifndef KEYBALL_SCROLLSNAP_ENABLE +# define KEYBALL_SCROLLSNAP_ENABLE 1 +#endif + +#ifndef KEYBALL_SCROLLSNAP_RESET_TIMER +# define KEYBALL_SCROLLSNAP_RESET_TIMER 100 +#endif + +#ifndef KEYBALL_SCROLLSNAP_TENSION_THRESHOLD +# define KEYBALL_SCROLLSNAP_TENSION_THRESHOLD 8 +#endif + ////////////////////////////////////////////////////////////////////////////// // Constants @@ -55,20 +67,20 @@ along with this program. If not, see . // Types enum keyball_keycodes { - KBC_RST = SAFE_RANGE, // Keyball configuration: reset to default - KBC_SAVE, // Keyball configuration: save to EEPROM + KBC_RST = SAFE_RANGE, // Keyball configuration: reset to default + KBC_SAVE, // Keyball configuration: save to EEPROM - CPI_I100, // CPI +100 CPI - CPI_D100, // CPI -100 CPI - CPI_I1K, // CPI +1000 CPI - CPI_D1K, // CPI -1000 CPI + CPI_I100, // CPI +100 CPI + CPI_D100, // CPI -100 CPI + CPI_I1K, // CPI +1000 CPI + CPI_D1K, // CPI -1000 CPI // In scroll mode, motion from primary trackball is treated as scroll // wheel. - SCRL_TO, // Toggle scroll mode - SCRL_MO, // Momentary scroll mode - SCRL_DVI, // Increment scroll divider - SCRL_DVD, // Decrement scroll divider + SCRL_TO, // Toggle scroll mode + SCRL_MO, // Momentary scroll mode + SCRL_DVI, // Increment scroll divider + SCRL_DVD, // Decrement scroll divider KEYBALL_SAFE_RANGE, }; @@ -77,12 +89,12 @@ typedef union { uint32_t raw; struct { uint8_t cpi : 7; - uint8_t sdiv : 3; // scroll divider + uint8_t sdiv : 3; // scroll divider }; } keyball_config_t; typedef struct { - uint8_t ballcnt; // count of balls: support only 0 or 1, for now + uint8_t ballcnt; // count of balls: support only 0 or 1, for now } keyball_info_t; typedef struct { @@ -104,8 +116,11 @@ typedef struct { bool cpi_changed; bool scroll_mode; + uint32_t scroll_mode_changed; uint8_t scroll_div; - uint32_t scroll_changed; + + uint32_t scroll_snap_last; + keyball_motion_t scroll_snap_tension; uint16_t last_kc; keypos_t last_pos; diff --git a/qmk_firmware/keyboards/keyball/lib/oledkit/oledkit.c b/qmk_firmware/keyboards/keyball/lib/oledkit/oledkit.c index b1a8f2e2a..4aec1cfc8 100644 --- a/qmk_firmware/keyboards/keyball/lib/oledkit/oledkit.c +++ b/qmk_firmware/keyboards/keyball/lib/oledkit/oledkit.c @@ -28,9 +28,13 @@ static const char PROGMEM logo[] = { 0}; // clang-format on -__attribute__((weak)) void oledkit_render_logo_user(void) { oled_write_P(logo, false); } +__attribute__((weak)) void oledkit_render_logo_user(void) { + oled_write_P(logo, false); +} -__attribute__((weak)) void oledkit_render_info_user(void) { oled_write_P(logo, false); } +__attribute__((weak)) void oledkit_render_info_user(void) { + oled_write_P(logo, false); +} __attribute__((weak)) bool oled_task_user(void) { if (is_keyboard_master()) { @@ -41,6 +45,8 @@ __attribute__((weak)) bool oled_task_user(void) { return true; } -__attribute__((weak)) oled_rotation_t oled_init_user(oled_rotation_t rotation) { return !is_keyboard_master() ? OLED_ROTATION_180 : rotation; } +__attribute__((weak)) oled_rotation_t oled_init_user(oled_rotation_t rotation) { + return !is_keyboard_master() ? OLED_ROTATION_180 : rotation; +} -#endif // OLED_ENABLE +#endif // OLED_ENABLE diff --git a/qmk_firmware/keyboards/keyball/lib/oledkit/oledkit.h b/qmk_firmware/keyboards/keyball/lib/oledkit/oledkit.h index bfdad0822..c8865eb45 100644 --- a/qmk_firmware/keyboards/keyball/lib/oledkit/oledkit.h +++ b/qmk_firmware/keyboards/keyball/lib/oledkit/oledkit.h @@ -31,4 +31,4 @@ void oledkit_render_info_user(void); // A keymap can override this by defining a function with same signature. void oledkit_render_logo_user(void); -#endif // OLED_ENABLE +#endif // OLED_ENABLE