Creating Classes (in C++) for Arduino

Classes are the fundamental construct of all OO (Object Oriented) programming languages. Most modern programming languages are OO (C++, Java, Php, Python, etc.). OO languages essentially deal with objects that have properties and can do certain things. The ‘class’ file defines what the available properties and functions are, and the ‘objects’ are instantiations (or ‘versions’) of those classes.

For example, a ‘car’ can be understood as a class … and a Peugeot 504 can be understood as an object. The ‘car’ class might have a property called ‘engine_size’ and the Peugeot 504 sets that property to be the value 1.9(L) (or whatever engine size 504’s used). A ‘car’ might also offer a function (or method in OO parlance) called start(). When start() is called on a car ( like this: car.start() ) … the car starts!

In this Spark, we go over how to create classes for the Arduino platform.

  • The Arduino language is a variant of C++ (i.e. it is mostly identical, with a few notable exceptions)
  • C++ Classes do not need header files, but most consider it good programming practice to use them. Some opinions can be found on stack oveflow and here
  • Arduino plugins are just Arduino classes.
  • Arduino classes are C++ classes with a few limitations:
    • no new and delete keywords
    • no exceptions
    • no libstdc++

Two useful Arduino class tutorials are:

  1. The standard Arduino one
  2. This Adafruit one where the class is *within* the sketch and does not use header file!

To create a CPP file within the same Arduino IDE window, see this stack overflow answer.

Create the necessary files (in the necessary place)

Start by creating both a header file and its corresponding cpp file. These need to be created in a folder inside the ~/Documents/Arduino/Libraries folder. For example, I’m going to create the following files:

  1. ~/Documents/Arduino/Libraries/Penpivot/Penpivot.h
  2. ~/Documents/Arduino/Libraries/Penpivot/Penpivot.cpp

You could use a simple text editor to create these files, or a proper code editor (such as Sublime Text).

Now open those files in your favourite text editor.

Screen Shot 2016-05-23 at 1.19.16 pm

I also like to create a “test” or sample project within the plugin / class folder. I usually place this in an ‘examples folder. So my folder hierarchy looks like this:

Screen Shot 2016-05-23 at 1.23.18 pm

Declare some methods

The first step is to declare some of methods that your class will make available to the Arduino Sketch. Start with only one or two methods (so that we can test the compilation). For example, in Penpivot.h, I am defining the following methods:

class Penpivot
{
  public:
    Penpivot( float leftWheelDiameter );
    void pivotLeft(float deg);
    void pivotRight(float deg);
   
  private:
    int translateAngleToStepperSteps(float angle);
    float _leftWheelDiamater;
    
};

public methods are methods that can be seen to code outside of the class. private methods are methods that only the code inside the class can use. There is a 3rd type: protected which is mainly used when building large packages of code (large plugins or platforms etc.). For the purposes of building a little Arduino plugin private and public will likely be largely sufficient.

Of course, I say this is the first step, but in reality this step will be constantly revisited as the class is revised, evolved and tested.

Test the compilation

Now that we have some code in our header file, we can test the compilation. This will just confirm that everything is in the right place and all the files are linking together properly.

You’ll need to make sure that your example Arduino sketch imports your class header file. Here’s what the default Arduino window (including the added #include directive) will look like:

#include <Penpivot.h>

void setup() {
  // put your setup code here, to run once:
}

void loop() {
  // put your main code here, to run repeatedly:
}

Here’s what my complete development environment then looks like: (note that the Arduino sketch called ‘example’ below isn’t the one saved to the plugin folder. Arduino doesn’t let its IDE save any sketches to the Libraries folder).

Screen Shot 2016-05-23 at 1.24.56 pm

Now, try to compile your code (by hitting the ‘tick’ button in the Arduino IDE). If all is good continue below. If you get a mistake go over the above steps.

If you find you have no problems then it can be a good idea to make a code error just to check to see if the compilation breaks. That way, you for sure than any future code errors will be picked up immediately.

Best practice header structure

It is highly possible that an external library will try to get imported multiple times (as a header file), so we need to make sure that we check if a library has already been imported. This check *wraps* the header file thus:

#ifndef Penpivot_h
#define Penpivot_h

#include "Arduino.h"
class Penpivot
{
  public:
    Penpivot( float leftWheelDiameter);
    void pivotLeft(float deg);
    void pivotRight(float deg);
   
  private:
    int translateAngleToStepperSteps(float angle);
    float _leftWheelDiamater;
    
};

#endif

Notice that in the above code I have also included the Arduino.h header file. This means that all methods exposed by the Arduino platform will also be available in the extra library/class being built.

Implementing the declarations

The header file just declares, or announces, to the compiler and to the other code which methods are going to be made available to them. The header file doesn’t actually involve writing any logic. The logic itself belongs within the *.cpp file.

As a start, write the below into your cpp file, and test the compilation

#include "Arduino.h"
#include "Penpivot.h"

Penpivot::Penpivot()
{
         _leftWheelDiameter = leftWheelDiameter;
}

Now lets make sure that all the methods in the header file are spelt out in the declaration file.

#include "Arduino.h"
#include "Penpivot.h"

Penpivot::Penpivot( float leftWheelDiameter)
{
        _leftWheelDiameter = leftWheelDiameter;
}

// Public Methods implementation

void Penpivot::pivotLeft(float deg)
{
	// this code is reponsible for pivoting the artbot to the left
}

void Penpivot::pivotRight(float deg)
{
	// this code is reponsible for pivoting the artbot to the right
	// Only the methods within this file can call the protected methods
	// So the next line works 
	int steps = translateAngleToStepperSteps(deg);

        // now tell the stepper to step steps amount.
}

// Private Methods implementation

int translateAngleToStepperSteps(float angle)
{
	// this code translates the desired pivot angle
	// into stepper steps for each respective wheel.
	// For now, it just returns any integer
	return 1;
}

Again, compile the code to make sure that nothing is broken. I’ll leave it up to you to fill in all of the above

Using the class in the Arduino Sketch

To use the class in the Arduino sketch requires that the header of the class is imported. Back in the Arduino IDE, you will need to instantiate (i.e. make an ‘Object’) the class by doing the following:

#include 

Penpivot myPivotingPen(55.5);

void setup() {
  // put your setup code here, to run once:
}

float deg = 0.0;
void loop() {
  deg = deg + 1;
  myPivotingPen.pivotRight(deg);
}

Of course, there are many more aspects to a class that the developer can use. Once this basic structure has been defined, however, the rest can be added incrementally.