Jump to content

Making "Button Press" Code Look Better (Arduino)

Hello,

    I'm starting small, and am trying to make a small macro keyboard consisting of 8 buttons, using an Arduino Pro Micro. I decided to borrow JChristensen's Arduino Button Library, and got one button to function correctly. The concern I have is when expanding this for multiple buttons.

    The process of using the library is to (after creating a button object) call the .read() method to update information regarding the object, then calling the .wasPressed() method to check if the button was pressed or not. However, the way I've done it below seems like a rather...inelegant(?) way of accomplishing it, and I was wondering if there was a better solution.

 

Spoiler

#include <Button.h>

//Creating Button Objects
Button buttonOne(2, true, true, 50); // Pin Number, Pullup, Logic Inversion, Debounce Time
Button buttonTwo(3, true, true, 50);
Button buttonThree(4, true, true, 50);
Button buttonFour(5, true, true, 50);
  ...so on and so forth until Button 8.
  
// Initialization
void setup()
{
  Serial.begin(9600);
}
  
// Main
void loop()
{
  // Check Button One
  buttonOne.read();
  if(buttonOne.wasPressed())
  {
  	Serial.println("Button One was Pressed"); // Macro will be added later.
  }
  
  // Check Button Two
  buttonTwo.read();
  if(buttonTwo.wasPressed())
  {
  	Serial.println("Button Two was Pressed"); // Macro will be added later.
  }
  
  // Check Button Three
  buttonThree.read();
  if(buttonThree.wasPressed())
  {
  	Serial.println("Button Three was Pressed"); // Macro will be added later.
  }
  
  // And so on and so forth

}

 

 

JChristensen's Arduino Button Library can be found here: https://github.com/JChristensen/Button

Link to comment
Share on other sites

Link to post
Share on other sites

4 hours ago, kennethnakasone said:

--SNIP--

I can't give you examples, as my coding for arduino-like chips etc is still rather novice. But I've made a quick search to see if its possible.

Basicly Classes would be a great option for you. You write one piece of code, where u can input and specify a button and for example a function to the button by calling instances of those classes.

If I'm not mistaken arduino uses C or C++ for their programming (or a dialect of some sorts)

So I'm going to give you a small PHP (yea go figure) example that would look somewhat similar. (as PHP language is based on C++ if I'm not mistaken)

 

<?php

class button{
  var $button;
  var $action;
  public function __construct($button, $action){
    $this->button = $button;
    $this->action = $action;
  }
  
  private function buttonAssignment(){
    /* insert code to assign the button to appropiate GPIO pin or something
    	forexample if u would make the variable $button = 1, that might be corrosponding to GPIO pin 1 or whatever
    */
  }
  
  private function actionAssignment(){
    /* Somewhat same here as the buttonAssignment
    Define certain functionality it needs to do according to $action. Lets say $action = "poweroff", then write a code that whenever $action = "poweroff" to poweroff the machine */
  }
}

/* then call the Class by making a new instance */

$button1 = new button(1, "poweroff");

?>

Again this is a PHP example, you still need to make it listen to the actual button press. But just to give you an idea what Classes could do for you. Also I am sort off aware that my PHP code there probably won't work at all even in PHP xD Didn't check for any mistakes or what so ever.

Main RIG: i7 4770k ~ 4.8Ghz | Intel HD Onboard (enough for my LoL gaming) | Samsung 960 Pro 256GB NVMe | 32GB (4x 8GB) Kingston Savage 2133Mhz DDR3 | MSI Z97 Gaming 7 | ThermalTake FrioOCK | MS-Tech (puke) 700W | Windows 10 64Bit

Mining RIG: AMD A6-9500 | ASRock AB350 Pro | 4GB DDR4 | 500GB 2.5 Inch HDD | 2x MSI AERO GTX 1060 6GB (Core/Memory/TDP/Avg Temp +160/+800/120%/45c) | 1x Asus Strix GTX 970 (+195/+400/125%/55c) | 1x KFA2 GTX 960 (+220/+500/120%/70c) | Corsair GS800 800W | HP HSTNS-PD05 1000W | (Modded) Inter-Tech IPC 4U-4129-N Rackmount Case

Guest RIG: FX6300 | AMD HD7870 | Kingston HyperX 128GB SSD | 16GB (2x 8GB) G.Skill Ripjaws 1600Mhz DDR3 | Some ASRock 970 Mobo | Stock Heatsink | some left over PSU  | Windows 10 64Bit

VM Server: HP Proliant DL160 G6 | 2x Intel Xeon E5620 @ 2.4Ghz 4c/8t (8c/16t total) | 16GB (8x 2GB) HP 1066Mhz ECC DDR3 | 2x Western Digital Black 250GB HDD | VMWare ESXI

Storage Node: 2x Intel Xeon E5520 @ 2.27Ghz 4c/8t (8c/16t total) | Intel ServerBoard S5500HCV | 36GB (9x 4GB) 1333Mhz ECC DDR3 | 3x Seagate 2TB 7200RPM | 4x Western Digital Caviar Green 2TB

Link to comment
Share on other sites

Link to post
Share on other sites

@Aelita Sophie, The arduino is not powerful enough for fully fledged object oriented programming. You cannot quite create and use classes and objects like in other systems.

Quote or tag if you want me to answer! PM me if you are in a real hurry!

Why do Java developers wear glasses? Because they can't C#!

 

My Machines:

The Gaming Rig:

Spoiler

-Processor: i5 6600k @4.6GHz

-Graphics: GTX1060 6GB G1 Gaming

-RAM: 2x8GB HyperX DDR4 2133MHz

-Motherboard: Asus Z170-A

-Cooler: Corsair H100i

-PSU: EVGA 650W 80+bronze

-AOC 1080p ultrawide

My good old laptop:

Spoiler

Lenovo T430

-Processor: i7 3520M

-4GB DDR3 1600MHz

-Graphics: intel iGPU :(

-Not even 1080p

 

Link to comment
Share on other sites

Link to post
Share on other sites

4 minutes ago, dany_boy said:

@Aelita Sophie, The arduino is not powerful enough for fully fledged object oriented programming. You cannot quite create and use classes and objects like in other systems.

Well it is limited ofcourse, but depending on his needs, OOP can be a neat solution for him. Or simply using functions would work great as well. Especially if the buttons are all somewhat the same, with the outcome as the only difference.

Main RIG: i7 4770k ~ 4.8Ghz | Intel HD Onboard (enough for my LoL gaming) | Samsung 960 Pro 256GB NVMe | 32GB (4x 8GB) Kingston Savage 2133Mhz DDR3 | MSI Z97 Gaming 7 | ThermalTake FrioOCK | MS-Tech (puke) 700W | Windows 10 64Bit

Mining RIG: AMD A6-9500 | ASRock AB350 Pro | 4GB DDR4 | 500GB 2.5 Inch HDD | 2x MSI AERO GTX 1060 6GB (Core/Memory/TDP/Avg Temp +160/+800/120%/45c) | 1x Asus Strix GTX 970 (+195/+400/125%/55c) | 1x KFA2 GTX 960 (+220/+500/120%/70c) | Corsair GS800 800W | HP HSTNS-PD05 1000W | (Modded) Inter-Tech IPC 4U-4129-N Rackmount Case

Guest RIG: FX6300 | AMD HD7870 | Kingston HyperX 128GB SSD | 16GB (2x 8GB) G.Skill Ripjaws 1600Mhz DDR3 | Some ASRock 970 Mobo | Stock Heatsink | some left over PSU  | Windows 10 64Bit

VM Server: HP Proliant DL160 G6 | 2x Intel Xeon E5620 @ 2.4Ghz 4c/8t (8c/16t total) | 16GB (8x 2GB) HP 1066Mhz ECC DDR3 | 2x Western Digital Black 250GB HDD | VMWare ESXI

Storage Node: 2x Intel Xeon E5520 @ 2.27Ghz 4c/8t (8c/16t total) | Intel ServerBoard S5500HCV | 36GB (9x 4GB) 1333Mhz ECC DDR3 | 3x Seagate 2TB 7200RPM | 4x Western Digital Caviar Green 2TB

Link to comment
Share on other sites

Link to post
Share on other sites

 

11 hours ago, dany_boy said:

-snip-

 

11 hours ago, Aelita Sophie said:

-snip-

 

Just as a heads-up/progress report: Making my own class was a bit daunting, so I opted for doing the program like this:

Spoiler


#include <Button.h>

//Creating Button Objects
Button buttonOne(2, true, true, 50); // Pin Number, Pullup, Logic Inversion, Debounce Time
Button buttonTwo(3, true, true, 50);
Button buttonThree(4, true, true, 50);
Button buttonFour(5, true, true, 50);
  ...so on and so forth until Button 8.
Button buttonArray[] = {buttonOne, buttonTwo, buttonThree, etc};
buttonArraySize = (sizeof(buttonArray)/18); //NOTE: Button Object occupies 18 bytes. Thus, dividing sizeOf(array) by 18 determines number of elements.
  
// Initialization
void setup()
{
  Serial.begin(9600);
}
  
// Main
void loop()
{
  for (int arrayPosition = 0; arrayPosition < buttonArraySize; ++arrayPosition)
  {
    buttonArray[arrayPosition].read();
    if (buttonArray[arrayPosition].isPressed() == true)
    {
      Serial.println("Button " + String(arrayPosition) + " is pressed");
    }  
  }
}

So, I made all of the buttons, put them (or rather, their references(?)) into an array, then used their position in the array to call the .read() and .isPressed() methods. Though I couldn't figure out a way to abbreviate the creation of button objects, the loop itself looks cleaner than before, so I'm happy with it for the time being.

 

I would like try making a class though. Ideally, the object itself would take the number of buttons as a parameter, and then allow the button to be pressed by using a method that takes the button's number as a parameter.

For example, for a class called Macropad:

// Object Creation

Macropad sampleMacropad( numberOfButtons, debounceTime, etc.);

 

Then, in the main function:

for (int buttonNumber = 0; buttonNumber < numberOfButtons; ++buttonNumber)

{

    sampleMacropad.pressButton(buttonNumber);

}

 

That way, I could simplify both the object creation, and button check/press code.

 

Thanks for the help!

Link to comment
Share on other sites

Link to post
Share on other sites

On 7/5/2017 at 0:11 PM, Aelita Sophie said:

Well it is limited ofcourse, but depending on his needs, OOP can be a neat solution for him. Or simply using functions would work great as well. Especially if the buttons are all somewhat the same, with the outcome as the only difference.

I wrote my code for my Arduino cooling routine in line as it was a first pass at coding it and then refactored it into reusable functions that made it a lot more maintainable.  You should try to use functions it will make it easier to do in the long run.

Link to comment
Share on other sites

Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×