From c37e4a6789ee0502372860467fcb616430465d0f Mon Sep 17 00:00:00 2001 From: annabunches <annabunches@gmail.com> Date: Mon, 1 Nov 2021 14:49:53 -0400 Subject: [PATCH 1/8] Add new behavior for a button that sends separate keypresses on press and release. This required a refactor of the button abstraction as well. --- Joystick.cpp | 50 +++++++++++++++++++++++++++++++++----------------- Joystick.h | 23 +++++++++++++++-------- Readme.md | 2 +- 3 files changed, 49 insertions(+), 26 deletions(-) diff --git a/Joystick.cpp b/Joystick.cpp index 57c76b5..738f423 100644 --- a/Joystick.cpp +++ b/Joystick.cpp @@ -1,5 +1,8 @@ #include "Joystick.h" #include <Arduino.h> +#include <list> + +using std::list; bool operator ==(JoyReport a, JoyReport b){ for (uint8_t i=0; i < JOYSTICK_NUM_AXES; i++) { @@ -17,16 +20,13 @@ bool operator !=(JoyReport a, JoyReport b){ Joystick::Joystick(bool debug) { _debug = debug; - _num_buttons = 0; + _last_button_index = 0; _num_axes = 0; _have_pulsed_button = false; for (uint8_t i=0; i < JOYSTICK_NUM_AXES; i++) { _joyReport.axis[i] = 0; } - for (uint8_t i=0; i < JOYSTICK_NUM_BYTES; i++) { - _joyReport.button[i] = 0; - } } void Joystick::Init() { @@ -42,9 +42,21 @@ void Joystick::AddButton(uint8_t pin, ButtonType type, bool pullup) { Button button; button.type = type; button.bouncer.attach(pin, mode); + uint8_t index = _last_button_index + 1; + uint8_t increment = 1; + button.index0 = index; - _buttons[_num_buttons] = button; - _num_buttons++; + if (type == BUTTON_PULSED_DOUBLE_ACTION_SPLIT) { + increment = 2; + button.index1 = index + 1; + } + + if (_last_button_index + increment > JOYSTICK_NUM_BUTTONS) { + // todo: fail here + } + + _buttons.push_back(button); + last_button_index += increment; if (type & _BUTTON_PULSED_TYPES) _have_pulsed_button = true; } @@ -57,8 +69,8 @@ void Joystick::AddAxis(uint8_t pin) { void Joystick::Update() { JoyReport oldReport = _joyReport; - for (int i = 0; i < _num_buttons; i++) { - _UpdateButton(i); + for (list<Button>::iterator cursor = _buttons.begin(); cursor != _buttons.end(); cursor++) { + _UpdateButton(*cursor); } for (int i = 0; i < _num_axes; i++) { @@ -100,8 +112,9 @@ void Joystick::ReleaseAllButtons() { } void Joystick::_ReleasePulsedButtons() { - for (uint8_t i = 0; i < _num_buttons; i++) { - if (_buttons[i].type & _BUTTON_PULSED_TYPES) ReleaseButton(i); + for (list<Button>::iterator i = _buttons.begin(); i != buttons.end(); i++) { + if (i->type & _BUTTON_PULSED_TYPES) ReleaseButton(i->index0); + if (i->type & BUTTON_PULSED_DOUBLE_ACTION_SPLIT) ReleaseButton(i->index1); } } @@ -124,20 +137,23 @@ void Joystick::Write() { delay(250); } -void Joystick::_UpdateButton(uint8_t index) { - Button* button = &_buttons[index]; +void Joystick::_UpdateButton(Button* button) { bool changed = button->bouncer.update(); switch (button->type) { - case BUTTON_LATCHED: - if (button->bouncer.rose()) PressButton(index); - else if (button->bouncer.fell()) ReleaseButton(index); + case BUTTON_PASSTHRU: + if (button->bouncer.rose()) PressButton(button->index0); + else if (button->bouncer.fell()) ReleaseButton(button->index0); break; case BUTTON_PULSED: - if (button->bouncer.rose()) PressButton(index); + if (button->bouncer.rose()) PressButton(button->index0); break; case BUTTON_PULSED_DOUBLE_ACTION: - if (changed) PressButton(index); + if (changed) PressButton(button->index0); + break; + case BUTTON_PULSED_DOUBLE_ACTION_SPLIT: + if (button->bouncer.rose()) PressButton(button->index0); + else if (button->bouncer.fell()) PressButton(button->index1); break; default: if (_debug) { diff --git a/Joystick.h b/Joystick.h index d1d3af6..8d95820 100644 --- a/Joystick.h +++ b/Joystick.h @@ -3,6 +3,9 @@ #include <Arduino.h> #include <Bounce2.h> +#include <list> + +using std::list; // If you're using the arduino-big-joystick firmware, these numbers can't be // changed. If you're writing your own Report Descriptor, tune these to match by @@ -16,9 +19,10 @@ #define JOYSTICK_NUM_BYTES (JOYSTICK_NUM_BUTTONS+7)/8 enum ButtonType { - BUTTON_LATCHED = 0x1, - BUTTON_PULSED = 0x2, - BUTTON_PULSED_DOUBLE_ACTION = 0x4 + BUTTON_PASSTHRU = 0x1, // always use the (debounced) absolute state of the input + BUTTON_PULSED = 0x2, // on button press, send an on signal followed immediately by an off signal. + BUTTON_PULSED_DOUBLE_ACTION = 0x4, // Send a button press twice - once for press and once for release. + BUTTON_PULSED_DOUBLE_ACTION_SPLIT = 0x8 // Send two separate button presses - one button on press, another on release. }; struct JoyReport { @@ -29,6 +33,9 @@ struct JoyReport { struct Button { ButtonType type; Bounce bouncer; + uint8_t index0; + uint8_t index1; + bool inverted = false; // if true, send button press on release and vice versa. }; bool operator ==(JoyReport a, JoyReport b); @@ -40,10 +47,10 @@ class Joystick { void Init(); void Update(); - void AddButton(uint8_t pin, ButtonType type, bool pullup=false); + void AddButton(uint8_t pin, ButtonType type, bool pullup=true); void AddAxis(uint8_t pin); // Axes don't actually work yet! - // These functions are deprecated and may become private in a future + // Public access to these functions is deprecated and they may become private in a future // version. Prefer the above API instead. void SetAxis(uint8_t axis, int16_t value); void PressButton(uint8_t button); @@ -56,8 +63,8 @@ class Joystick { void _UpdateButton(uint8_t index); void _UpdateAxis(uint8_t index); - Button _buttons[JOYSTICK_NUM_BUTTONS]; - uint8_t _num_buttons; + list<Button> _buttons; + uint8_t _last_button_index; bool _have_pulsed_button; uint8_t _axes[JOYSTICK_NUM_AXES]; @@ -68,6 +75,6 @@ class Joystick { }; // Internal use only. -#define _BUTTON_PULSED_TYPES (BUTTON_PULSED | BUTTON_PULSED_DOUBLE_ACTION) +#define _BUTTON_PULSED_TYPES (BUTTON_PULSED | BUTTON_PULSED_DOUBLE_ACTION | BUTTON_PULSED_DOUBLE_ACTION_SPLIT) #endif diff --git a/Readme.md b/Readme.md index 845e609..3d12ea6 100644 --- a/Readme.md +++ b/Readme.md @@ -2,7 +2,7 @@ This is a library that builds and sends USB HID Joystick reports, making it easy to build USB Joysticks with Arduino. ## Dependencies -* Your Arduino's USB communication chip be programmed with the arduino-big-joystick firmware (or similar). See <https://github.com/harlequin-tech/arduino-usb> for more info. +* Your Arduino's USB communication chip must be programmed with the arduino-big-joystick firmware (or similar). See <https://github.com/harlequin-tech/arduino-usb> for more info. * The Bounce2 library, available at <https://github.com/thomasfredericks/Bounce2>. ## Installation From 6a692687f5511349629961fcfddd1891076a866e Mon Sep 17 00:00:00 2001 From: annabunches <annabunches@gmail.com> Date: Mon, 1 Nov 2021 15:24:05 -0400 Subject: [PATCH 2/8] Add BUTTON_LATCHED_MOMENTARY type, to allow a pushbutton to mimic the behavior of a toggle switch. --- Joystick.cpp | 12 +++++++++++- Joystick.h | 6 ++++-- examples/type_test/type_test.ino | 22 ++++++++++++++++++++++ 3 files changed, 37 insertions(+), 3 deletions(-) create mode 100644 examples/type_test/type_test.ino diff --git a/Joystick.cpp b/Joystick.cpp index 738f423..9712454 100644 --- a/Joystick.cpp +++ b/Joystick.cpp @@ -50,7 +50,7 @@ void Joystick::AddButton(uint8_t pin, ButtonType type, bool pullup) { increment = 2; button.index1 = index + 1; } - + if (_last_button_index + increment > JOYSTICK_NUM_BUTTONS) { // todo: fail here } @@ -155,6 +155,16 @@ void Joystick::_UpdateButton(Button* button) { if (button->bouncer.rose()) PressButton(button->index0); else if (button->bouncer.fell()) PressButton(button->index1); break; + case BUTTON_LATCHED_MOMENTARY: + if (button->bouncer.rose()) { + if !(button->pressed) { + PressButton(button->index0); + button->pressed = true; + } else { + ReleaseButton(button->index0); + button->pressed = false; + } + break; default: if (_debug) { Serial.print("DEBUG: Unhandled button type: "); diff --git a/Joystick.h b/Joystick.h index 8d95820..32cc0a4 100644 --- a/Joystick.h +++ b/Joystick.h @@ -22,7 +22,8 @@ enum ButtonType { BUTTON_PASSTHRU = 0x1, // always use the (debounced) absolute state of the input BUTTON_PULSED = 0x2, // on button press, send an on signal followed immediately by an off signal. BUTTON_PULSED_DOUBLE_ACTION = 0x4, // Send a button press twice - once for press and once for release. - BUTTON_PULSED_DOUBLE_ACTION_SPLIT = 0x8 // Send two separate button presses - one button on press, another on release. + BUTTON_PULSED_DOUBLE_ACTION_SPLIT = 0x8, // Send two separate button presses - one button on press, another on release. + BUTTON_LATCHED_MOMENTARY = 0x10 }; struct JoyReport { @@ -34,7 +35,8 @@ struct Button { ButtonType type; Bounce bouncer; uint8_t index0; - uint8_t index1; + uint8_t index1; // only used by BUTTON_PULSED_DOUBLE_ACTION_SPLIT + bool pressed = false; // only used by BUTTON_LATCHED_MOMENTARY bool inverted = false; // if true, send button press on release and vice versa. }; diff --git a/examples/type_test/type_test.ino b/examples/type_test/type_test.ino new file mode 100644 index 0000000..03f6e35 --- /dev/null +++ b/examples/type_test/type_test.ino @@ -0,0 +1,22 @@ +// An example sketch using the joystick library. +// In this example, we have 3 toggle switches and 2 momentary pushbuttons. +// Each button is configured in a different one of the available behaviors. + +#include <Bounce2.h> +#include <Joystick.h> + +bool debug = false; +Joystick joystick(debug); + +void setup() { + joystick.AddButton(9, BUTTON_PASSTHRU); + joystick.AddButton(10, BUTTON_LATCHED_MOMENTARY); + joystick.AddButton(11, BUTTON_PULSED); + joystick.AddButton(12, BUTTON_PULSED_DOUBLE_ACTION); + joystick.AddButton(13, BUTTON_PULSED_DOUBLE_ACTION_SPLIT); + joystick.Init(); +} + +void loop() { + joystick.Update(); +} From 5322744f4213ee9384f0915d4e1737d86fb9cf25 Mon Sep 17 00:00:00 2001 From: annabunches <annabunches@gmail.com> Date: Mon, 1 Nov 2021 15:38:01 -0400 Subject: [PATCH 3/8] Revert to non-STL-using code, since that's not available when compiling for Arduino... --- Joystick.cpp | 16 +++++++++------- Joystick.h | 5 +++-- 2 files changed, 12 insertions(+), 9 deletions(-) diff --git a/Joystick.cpp b/Joystick.cpp index 9712454..de8e1e0 100644 --- a/Joystick.cpp +++ b/Joystick.cpp @@ -55,7 +55,8 @@ void Joystick::AddButton(uint8_t pin, ButtonType type, bool pullup) { // todo: fail here } - _buttons.push_back(button); + _buttons[_num_buttons] = button; + _num_buttons++; last_button_index += increment; if (type & _BUTTON_PULSED_TYPES) _have_pulsed_button = true; @@ -69,8 +70,8 @@ void Joystick::AddAxis(uint8_t pin) { void Joystick::Update() { JoyReport oldReport = _joyReport; - for (list<Button>::iterator cursor = _buttons.begin(); cursor != _buttons.end(); cursor++) { - _UpdateButton(*cursor); + for (uint i = 0; i < _num_buttons; i++) { + _UpdateButton(i); } for (int i = 0; i < _num_axes; i++) { @@ -112,9 +113,9 @@ void Joystick::ReleaseAllButtons() { } void Joystick::_ReleasePulsedButtons() { - for (list<Button>::iterator i = _buttons.begin(); i != buttons.end(); i++) { - if (i->type & _BUTTON_PULSED_TYPES) ReleaseButton(i->index0); - if (i->type & BUTTON_PULSED_DOUBLE_ACTION_SPLIT) ReleaseButton(i->index1); + for (uint8_t i = 0; i < _num_buttons; i++ ) { + if (i->type & _BUTTON_PULSED_TYPES) ReleaseButton(_buttons[i].index0); + if (i->type & BUTTON_PULSED_DOUBLE_ACTION_SPLIT) ReleaseButton(_buttons[i].index1); } } @@ -137,7 +138,8 @@ void Joystick::Write() { delay(250); } -void Joystick::_UpdateButton(Button* button) { +void Joystick::_UpdateButton(uint8_t button_num) { + Button *button = &_button[button_num]; bool changed = button->bouncer.update(); switch (button->type) { diff --git a/Joystick.h b/Joystick.h index 32cc0a4..3e88523 100644 --- a/Joystick.h +++ b/Joystick.h @@ -65,8 +65,9 @@ class Joystick { void _UpdateButton(uint8_t index); void _UpdateAxis(uint8_t index); - list<Button> _buttons; - uint8_t _last_button_index; + Button _buttons[JOYSTICK_NUM_BUTTONS]; + uint8_t _num_buttons; + uint8_t _last_button_index; // a single physical button can have multiple logical buttons. _last_button_index tracks the number of logical / virtual buttons we have defined. bool _have_pulsed_button; uint8_t _axes[JOYSTICK_NUM_AXES]; From 6ea618776913bab2874f1bc036c604772c860ed5 Mon Sep 17 00:00:00 2001 From: annabunches <annabunches@gmail.com> Date: Mon, 1 Nov 2021 15:38:39 -0400 Subject: [PATCH 4/8] Remove now-useless includes. --- Joystick.cpp | 1 - Joystick.h | 1 - 2 files changed, 2 deletions(-) diff --git a/Joystick.cpp b/Joystick.cpp index de8e1e0..aded9f5 100644 --- a/Joystick.cpp +++ b/Joystick.cpp @@ -1,6 +1,5 @@ #include "Joystick.h" #include <Arduino.h> -#include <list> using std::list; diff --git a/Joystick.h b/Joystick.h index 3e88523..cca7225 100644 --- a/Joystick.h +++ b/Joystick.h @@ -3,7 +3,6 @@ #include <Arduino.h> #include <Bounce2.h> -#include <list> using std::list; From 2a35a862307132135b0065e3cbf5f7d2356c7b52 Mon Sep 17 00:00:00 2001 From: annabunches <annabunches@gmail.com> Date: Mon, 1 Nov 2021 15:39:13 -0400 Subject: [PATCH 5/8] Reverting more cruft. --- Joystick.cpp | 2 -- Joystick.h | 2 -- 2 files changed, 4 deletions(-) diff --git a/Joystick.cpp b/Joystick.cpp index aded9f5..23613dd 100644 --- a/Joystick.cpp +++ b/Joystick.cpp @@ -1,8 +1,6 @@ #include "Joystick.h" #include <Arduino.h> -using std::list; - bool operator ==(JoyReport a, JoyReport b){ for (uint8_t i=0; i < JOYSTICK_NUM_AXES; i++) { if (a.axis[i] != b.axis[i]) return false; diff --git a/Joystick.h b/Joystick.h index cca7225..98cf64d 100644 --- a/Joystick.h +++ b/Joystick.h @@ -4,8 +4,6 @@ #include <Arduino.h> #include <Bounce2.h> -using std::list; - // If you're using the arduino-big-joystick firmware, these numbers can't be // changed. If you're writing your own Report Descriptor, tune these to match by // defining them *before* you include Joystick.h. From 398668205da4e5ef22f610b3677324fcf495352b Mon Sep 17 00:00:00 2001 From: annabunches <annabunches@gmail.com> Date: Mon, 1 Nov 2021 15:44:32 -0400 Subject: [PATCH 6/8] Fixed various errors. --- Joystick.cpp | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/Joystick.cpp b/Joystick.cpp index 23613dd..0814b09 100644 --- a/Joystick.cpp +++ b/Joystick.cpp @@ -54,7 +54,7 @@ void Joystick::AddButton(uint8_t pin, ButtonType type, bool pullup) { _buttons[_num_buttons] = button; _num_buttons++; - last_button_index += increment; + _last_button_index += increment; if (type & _BUTTON_PULSED_TYPES) _have_pulsed_button = true; } @@ -67,11 +67,11 @@ void Joystick::AddAxis(uint8_t pin) { void Joystick::Update() { JoyReport oldReport = _joyReport; - for (uint i = 0; i < _num_buttons; i++) { + for (uint8_t i = 0; i < _num_buttons; i++) { _UpdateButton(i); } - for (int i = 0; i < _num_axes; i++) { + for (uint8_t i = 0; i < _num_axes; i++) { _UpdateAxis(i); } @@ -111,8 +111,9 @@ void Joystick::ReleaseAllButtons() { void Joystick::_ReleasePulsedButtons() { for (uint8_t i = 0; i < _num_buttons; i++ ) { - if (i->type & _BUTTON_PULSED_TYPES) ReleaseButton(_buttons[i].index0); - if (i->type & BUTTON_PULSED_DOUBLE_ACTION_SPLIT) ReleaseButton(_buttons[i].index1); + Button button = _buttons[i]; + if (button.type & _BUTTON_PULSED_TYPES) ReleaseButton(button.index0); + if (button.type & BUTTON_PULSED_DOUBLE_ACTION_SPLIT) ReleaseButton(button.index1); } } @@ -136,7 +137,7 @@ void Joystick::Write() { } void Joystick::_UpdateButton(uint8_t button_num) { - Button *button = &_button[button_num]; + Button *button = &_buttons[button_num]; bool changed = button->bouncer.update(); switch (button->type) { @@ -156,13 +157,14 @@ void Joystick::_UpdateButton(uint8_t button_num) { break; case BUTTON_LATCHED_MOMENTARY: if (button->bouncer.rose()) { - if !(button->pressed) { + if (!button->pressed) { PressButton(button->index0); button->pressed = true; } else { ReleaseButton(button->index0); button->pressed = false; } + } break; default: if (_debug) { From 3fd595c7c2ac171801537d55b6f7ec8925ff36d8 Mon Sep 17 00:00:00 2001 From: Anna Wiggins <annabunches@gmail.com> Date: Mon, 1 Nov 2021 22:09:11 +0000 Subject: [PATCH 7/8] Rename variables for clarity, fix enumeration bug. --- .gitignore | 2 ++ Joystick.cpp | 31 +++++++++++++++---------------- Joystick.h | 6 +++--- examples/type_test/type_test.ino | 2 +- 4 files changed, 21 insertions(+), 20 deletions(-) create mode 100644 .gitignore diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..d6c2e45 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +*.elf +*.hex diff --git a/Joystick.cpp b/Joystick.cpp index 0814b09..97fcb0e 100644 --- a/Joystick.cpp +++ b/Joystick.cpp @@ -17,7 +17,7 @@ bool operator !=(JoyReport a, JoyReport b){ Joystick::Joystick(bool debug) { _debug = debug; - _last_button_index = 0; + _virtual_buttons = 0; _num_axes = 0; _have_pulsed_button = false; @@ -39,22 +39,21 @@ void Joystick::AddButton(uint8_t pin, ButtonType type, bool pullup) { Button button; button.type = type; button.bouncer.attach(pin, mode); - uint8_t index = _last_button_index + 1; uint8_t increment = 1; - button.index0 = index; + button.vbutton0 = _virtual_buttons; if (type == BUTTON_PULSED_DOUBLE_ACTION_SPLIT) { increment = 2; - button.index1 = index + 1; + button.vbutton1 = _virtual_buttons + 1; } - if (_last_button_index + increment > JOYSTICK_NUM_BUTTONS) { + if (_virtual_buttons + increment > JOYSTICK_NUM_BUTTONS) { // todo: fail here } _buttons[_num_buttons] = button; _num_buttons++; - _last_button_index += increment; + _virtual_buttons += increment; if (type & _BUTTON_PULSED_TYPES) _have_pulsed_button = true; } @@ -112,8 +111,8 @@ void Joystick::ReleaseAllButtons() { void Joystick::_ReleasePulsedButtons() { for (uint8_t i = 0; i < _num_buttons; i++ ) { Button button = _buttons[i]; - if (button.type & _BUTTON_PULSED_TYPES) ReleaseButton(button.index0); - if (button.type & BUTTON_PULSED_DOUBLE_ACTION_SPLIT) ReleaseButton(button.index1); + if (button.type & _BUTTON_PULSED_TYPES) ReleaseButton(button.vbutton0); + if (button.type & BUTTON_PULSED_DOUBLE_ACTION_SPLIT) ReleaseButton(button.vbutton1); } } @@ -142,26 +141,26 @@ void Joystick::_UpdateButton(uint8_t button_num) { switch (button->type) { case BUTTON_PASSTHRU: - if (button->bouncer.rose()) PressButton(button->index0); - else if (button->bouncer.fell()) ReleaseButton(button->index0); + if (button->bouncer.rose()) PressButton(button->vbutton0); + else if (button->bouncer.fell()) ReleaseButton(button->vbutton0); break; case BUTTON_PULSED: - if (button->bouncer.rose()) PressButton(button->index0); + if (button->bouncer.rose()) PressButton(button->vbutton0); break; case BUTTON_PULSED_DOUBLE_ACTION: - if (changed) PressButton(button->index0); + if (changed) PressButton(button->vbutton0); break; case BUTTON_PULSED_DOUBLE_ACTION_SPLIT: - if (button->bouncer.rose()) PressButton(button->index0); - else if (button->bouncer.fell()) PressButton(button->index1); + if (button->bouncer.rose()) PressButton(button->vbutton0); + else if (button->bouncer.fell()) PressButton(button->vbutton1); break; case BUTTON_LATCHED_MOMENTARY: if (button->bouncer.rose()) { if (!button->pressed) { - PressButton(button->index0); + PressButton(button->vbutton0); button->pressed = true; } else { - ReleaseButton(button->index0); + ReleaseButton(button->vbutton0); button->pressed = false; } } diff --git a/Joystick.h b/Joystick.h index 98cf64d..9802925 100644 --- a/Joystick.h +++ b/Joystick.h @@ -31,8 +31,8 @@ struct JoyReport { struct Button { ButtonType type; Bounce bouncer; - uint8_t index0; - uint8_t index1; // only used by BUTTON_PULSED_DOUBLE_ACTION_SPLIT + uint8_t vbutton0; + uint8_t vbutton1; // only used by BUTTON_PULSED_DOUBLE_ACTION_SPLIT bool pressed = false; // only used by BUTTON_LATCHED_MOMENTARY bool inverted = false; // if true, send button press on release and vice versa. }; @@ -64,7 +64,7 @@ class Joystick { Button _buttons[JOYSTICK_NUM_BUTTONS]; uint8_t _num_buttons; - uint8_t _last_button_index; // a single physical button can have multiple logical buttons. _last_button_index tracks the number of logical / virtual buttons we have defined. + uint8_t _virtual_buttons; // a single user-defined button can have multiple virtual buttons. bool _have_pulsed_button; uint8_t _axes[JOYSTICK_NUM_AXES]; diff --git a/examples/type_test/type_test.ino b/examples/type_test/type_test.ino index 03f6e35..14199bb 100644 --- a/examples/type_test/type_test.ino +++ b/examples/type_test/type_test.ino @@ -5,7 +5,7 @@ #include <Bounce2.h> #include <Joystick.h> -bool debug = false; +bool debug = true; Joystick joystick(debug); void setup() { From bcfd67b50df1cfc2fa324fecee9b59776a6aeb01 Mon Sep 17 00:00:00 2001 From: Anna Wiggins <annabunches@gmail.com> Date: Mon, 1 Nov 2021 22:19:05 +0000 Subject: [PATCH 8/8] Fix behavior when using pull-up resistors. --- Joystick.cpp | 19 ++++++++++++------- examples/type_test/Makefile | 8 ++++++++ examples/type_test/type_test.ino | 2 +- 3 files changed, 21 insertions(+), 8 deletions(-) create mode 100644 examples/type_test/Makefile diff --git a/Joystick.cpp b/Joystick.cpp index 97fcb0e..5b4c99a 100644 --- a/Joystick.cpp +++ b/Joystick.cpp @@ -38,6 +38,7 @@ void Joystick::AddButton(uint8_t pin, ButtonType type, bool pullup) { Button button; button.type = type; + button.inverted = pullup; button.bouncer.attach(pin, mode); uint8_t increment = 1; button.vbutton0 = _virtual_buttons; @@ -138,24 +139,28 @@ void Joystick::Write() { void Joystick::_UpdateButton(uint8_t button_num) { Button *button = &_buttons[button_num]; bool changed = button->bouncer.update(); + if (!changed) return; + + bool on = button->bouncer.rose(); + if (button->inverted) on = button->bouncer.fell(); switch (button->type) { case BUTTON_PASSTHRU: - if (button->bouncer.rose()) PressButton(button->vbutton0); - else if (button->bouncer.fell()) ReleaseButton(button->vbutton0); + if (on) PressButton(button->vbutton0); + else ReleaseButton(button->vbutton0); break; case BUTTON_PULSED: - if (button->bouncer.rose()) PressButton(button->vbutton0); + if (on) PressButton(button->vbutton0); break; case BUTTON_PULSED_DOUBLE_ACTION: - if (changed) PressButton(button->vbutton0); + PressButton(button->vbutton0); break; case BUTTON_PULSED_DOUBLE_ACTION_SPLIT: - if (button->bouncer.rose()) PressButton(button->vbutton0); - else if (button->bouncer.fell()) PressButton(button->vbutton1); + if (on) PressButton(button->vbutton0); + else PressButton(button->vbutton1); break; case BUTTON_LATCHED_MOMENTARY: - if (button->bouncer.rose()) { + if (on) { if (!button->pressed) { PressButton(button->vbutton0); button->pressed = true; diff --git a/examples/type_test/Makefile b/examples/type_test/Makefile new file mode 100644 index 0000000..d1058d4 --- /dev/null +++ b/examples/type_test/Makefile @@ -0,0 +1,8 @@ +TARGET_BOARD=arduino:avr:uno +COM_PORT=/dev/ttyACM0 + +build: + arduino-cli compile -b ${TARGET_BOARD} + +upload: + arduino-cli upload -b ${TARGET_BOARD} -p ${COM_PORT} diff --git a/examples/type_test/type_test.ino b/examples/type_test/type_test.ino index 14199bb..03f6e35 100644 --- a/examples/type_test/type_test.ino +++ b/examples/type_test/type_test.ino @@ -5,7 +5,7 @@ #include <Bounce2.h> #include <Joystick.h> -bool debug = true; +bool debug = false; Joystick joystick(debug); void setup() {