Skip to content

Commit

Permalink
update blutton class to match the standard puara-gestures API
Browse files Browse the repository at this point in the history
  • Loading branch information
edumeneses committed Feb 20, 2025
1 parent e4b1ff9 commit eeac2fb
Showing 1 changed file with 138 additions and 78 deletions.
216 changes: 138 additions & 78 deletions include/puara/descriptors/button.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,144 +6,204 @@
namespace puara_gestures
{

class button
/**
* @brief This class extract several features from a discrete value, e.g., a button.
*
* It expects a discete value (an int with value 0 or 1).
*
* Button can use `tied_data`, which is an external variable that users update on their own.
* Users can then call update() without any argumments to extract the features from the `tied_data`.
* The usage should be:
* setup:
* - user creates variable, e.g. button_data
* user instantiates the class, e.g. puara::Button my_button(button_data)
* loop/task:
* - user saves sensor value into button_data
* - user/task calls my_button.update()
* - user accesses button descriptors with my_button functions
*/
class Button
{
private:
unsigned int buttonCount = 0;
unsigned int buttonCountInterval = 200;
int buttonValue = 0;
bool buttonPress = false;
unsigned int buttonTap = 0;
unsigned int buttonDtap = 0;
unsigned int buttonTtap = 0;
bool buttonHold = false;
unsigned int buttonHoldInterval = 5000;
unsigned int buttonFilterPeriod = 10;
long buttonTimer = 0;
unsigned long buttonPressTime = 0;
unsigned int buttonThreshold = 1;
long long getCurrentTimeMicroseconds();
long timer = 0;
int tied_data = 0;

public:
void updateButton(int buttonValue)
Button() noexcept
: tied_data(nullptr)
{
}

Button(const Button&) noexcept = default;
Button(Button&&) noexcept = default;
Button& operator=(const Button&) noexcept = default;
Button& operator=(Button&&) noexcept = default;

explicit Button(int* tied)
: threshold(5)
, tied_data(tied)
{
}

unsigned int count = 0;
bool press = false;
unsigned int tap = 0;
unsigned int doubleTap = 0;
unsigned int tripleTap = 0;
bool hold = false;
unsigned long pressTime = 0;
unsigned int threshold = 1;
unsigned int countInterval = 200;
unsigned int holdInterval = 5000;

void update(int value)
{
long currentTime = getCurrentTimeMicroseconds() / 999LL;
buttonValue = buttonValue;
if(buttonValue < buttonThreshold)
tied_data = value;
if(value < threshold)
{
if(!buttonPress)
if(!press)
{
buttonPress = true;
buttonTimer = currentTime;
press = true;
timer = currentTime;
}
if(currentTime - buttonTimer > buttonHoldInterval)
if(currentTime - timer > holdInterval)
{
buttonHold = true;
hold = true;
}
}
else if(buttonHold)
else if(hold)
{
buttonHold = false;
buttonPress = false;
buttonCount = 0;
hold = false;
press = false;
count = 0;
}
else
{
if(buttonPress)
if(press)
{
buttonPress = false;
buttonPressTime = currentTime - buttonTimer;
buttonTimer = currentTime;
buttonCount++;
press = false;
pressTime = currentTime - timer;
timer = currentTime;
count++;
}
}
if(!buttonPress && (currentTime - buttonTimer > buttonCountInterval))
if(!press && (currentTime - timer > countInterval))
{
switch(buttonCount)
switch(count)
{
case 0:
buttonTap = 0;
buttonDtap = 0;
buttonTtap = 0;
tap = 0;
doubleTap = 0;
tripleTap = 0;
break;
case 1:
buttonTap = 1;
buttonDtap = 0;
buttonTtap = 0;
tap = 1;
doubleTap = 0;
tripleTap = 0;
break;
case 2:
buttonTap = 0;
buttonDtap = 1;
buttonTtap = 0;
tap = 0;
doubleTap = 1;
tripleTap = 0;
break;
case 3:
buttonTap = 0;
buttonDtap = 0;
buttonTtap = 1;
tap = 0;
doubleTap = 0;
tripleTap = 1;
break;
}
buttonCount = 0;
count = 0;
}
}

int update()
{
if(tied_data != nullptr)
{
Button::update(*tied_data);
return 1;
}
else
{
// should we assert here, it seems like an error to call update() without a tied_value?
return 0;
}
}

void updateTrigButton(int buttonValue)
void updateTrigButton(int value)
{
long currentTime = getCurrentTimeMicroseconds() / 999LL;
buttonValue = buttonValue;
if(buttonValue >= buttonThreshold)
value = value;
if(value >= threshold)
{
if(!buttonPress)
if(!press)
{
buttonPress = true;
buttonTimer = currentTime;
press = true;
timer = currentTime;
}
if(currentTime - buttonTimer > buttonHoldInterval)
if(currentTime - timer > holdInterval)
{
buttonHold = true;
hold = true;
}
}
else if(buttonHold)
else if(hold)
{
buttonHold = false;
buttonPress = false;
buttonCount = -1;
hold = false;
press = false;
count = -1;
}
else
{
if(buttonPress)
if(press)
{
buttonPress = false;
buttonPressTime = currentTime - buttonTimer;
buttonTimer = currentTime;
buttonCount++;
press = false;
pressTime = currentTime - timer;
timer = currentTime;
count++;
}
}
if(!buttonPress && (currentTime - buttonTimer > buttonCountInterval))
if(!press && (currentTime - timer > countInterval))
{
switch(buttonCount)
switch(count)
{
case 0:
buttonTap = 0;
buttonDtap = 0;
buttonTtap = 0;
tap = 0;
doubleTap = 0;
tripleTap = 0;
break;
case 1:
buttonTap = 1;
buttonDtap = 0;
buttonTtap = 0;
tap = 1;
doubleTap = 0;
tripleTap = 0;
break;
case 2:
buttonTap = 0;
buttonDtap = 1;
buttonTtap = 0;
tap = 0;
doubleTap = 1;
tripleTap = 0;
break;
case 3:
buttonTap = 0;
buttonDtap = 0;
buttonTtap = 1;
tap = 0;
doubleTap = 0;
tripleTap = 1;
break;
}
buttonCount = 0;
count = 0;
}
}

int updateTrigButton()
{
if(tied_data != nullptr)
{
Button::updateTrigButton(*tied_data);
return 1;
}
else
{
// should we assert here, it seems like an error to call update() without a tied_value?
return 0;
}
}
};
Expand Down

0 comments on commit eeac2fb

Please sign in to comment.