-
Hi @luni64 , I am trying to come up with a callback method for short and long button presses using the EncoderTool library and my coding skills aren't that great in coming up with the solution. I've tried to adapt an example I have found on the web to this library and I am only able to get it working in the loop but I am overlooking something when I use the button callback. I can only get the short press to respond. Does this have something to do with how the Bounce2 library is configured by default in the EncoderTool library? Here is the working code in the loop:
|
Beta Was this translation helpful? Give feedback.
Replies: 8 comments 6 replies
-
This should work: #include "Arduino.h"
#include "EncoderTool.h"
using namespace EncoderTool;
PolledEncoder encoder; // Polling encoder, please call corresponding tick() functions as often as possible, e.g. in loop
void onButtonChanged(int32_t state)
{
static uint32_t lastTime;
if (state == LOW)
{
Serial.println("Button Down");
lastTime = millis();
}
else // button released
{
if (millis() - lastTime < 1000)
Serial.println("Short Press\n");
else
Serial.println("Long Press\n");
}
}
void setup()
{
encoder.begin(0, 1, 2);
encoder.attachButtonCallback(onButtonChanged); // connect the button callback function
}
void loop()
{
encoder.tick();
} Prints
|
Beta Was this translation helpful? Give feedback.
-
In this case you can't do it in the callback alone since this is only invoked if the button changed. But it is easy to use a timer for this: #include "Arduino.h"
#include "EncoderTool.h"
using namespace EncoderTool;
PolledEncoder encoder;
IntervalTimer btnTimer;
bool timerRunning = false; // unfortunately the timer has no built in way to find out if it's running
constexpr unsigned longPressTime = 1'000'000; // us
void onLongPress()
{
btnTimer.end(); // trigger only once
timerRunning = false;
Serial.println("Long Press\n");
// do whatever need to be done on a long press here...
}
void onButtonChanged(int32_t state)
{
if (state == LOW) // button pressed
{ //
btnTimer.begin(onLongPress, longPressTime); // start timer to detect long press
timerRunning = true;
Serial.println("Button down");
}
else // button released
{
if (timerRunning) // timer not elapsed when button was released -> short press
{
btnTimer.end(); // stop the timer since we detected a short press
Serial.println("Short Press\n");
// do whatever need to be done on a short press here...
}
}
}
void setup()
{
encoder.begin(0, 1, 2);
encoder.attachButtonCallback(onButtonChanged);
}
void loop()
{
encoder.tick();
} |
Beta Was this translation helpful? Give feedback.
-
You definitely need some timing mechanism if you want the long press event asynchronous to the actual button changes. You could of course make you own timer using millis but you would probably end up with the same mess as shown in your first post.
There are 4 IntervalTimers available. As long as you don't use them up completely you should be fine.
There is a XIAO branch of the library. Did you try this? I don't know much about the XIAO but I assume there will be a similar timer for the board which you could use. |
Beta Was this translation helpful? Give feedback.
-
Understood - definitely trying to avoid methods that could prove problematic going forward.
Ok great! This shouldn't be an issue.
I am aware of the XIAO branch but haven't tried yet. From what little I have read, there does not seem to be IntervalTimer support but there are interrupt timers: https://www.sigmdel.ca/michel/ha/xiao/seeeduino_xiao_01_en.html#timers and here. I have the XIAO and need to get the circuit on a breadboard. I will let you know how it goes asap. Thank you again for all your help so far. I am learning so much! |
Beta Was this translation helpful? Give feedback.
-
I just wanted to report back that the XIAO branch of the library works great! Also, I modified the above example for use with |
Beta Was this translation helpful? Give feedback.
-
Great! |
Beta Was this translation helpful? Give feedback.
-
@m-r-m-s I just released a new version (v3.0.0) which should be platform independent. Would be great if you could test it for the XIAO as well :-) |
Beta Was this translation helpful? Give feedback.
-
Thanks for testing. I'll fix the examples accordingly. Let me know if this fixes it for you. |
Beta Was this translation helpful? Give feedback.
In this case you can't do it in the callback alone since this is only invoked if the button changed. But it is easy to use a timer for this: