Arduino Playground is read-only starting December 31st, 2018. For more info please look at this Forum Post

How To Extend A Library Using Hierarchy

<under construction>


Navigation


What is hierarchy?

A hierarchy is a pyramidal arrangement of items (objects, names, values, categories, etc.), in which the items are represented as being "above," "below," or "at the same level as" one another. Wikipedia

Hierarchy is just a technical way of describing the relationship between classes in c++. You would probably not hesitate if I said Both a Circle and a Triangle are a Shape but it might seem weird if I say that Both class Circle and class Triangle inherits from class Shape

Hierarchy is also a way of making a project modular.
If you have a set of classes that you can choose from, building a new class becomes much easier.
Say you'll want to make a new class called TemperatureSensor, this class will need to provide the user with:
void begin();
int read();
void debug(char* debugString);

Let's say you have access to these classes:
#ifndef DEBUGGABLE_H
#define DEBUGGABLE_H
class Debuggable {
    public:
        inline void debug(char* debugString){ 
            Serial.println(debugString); 
        }
};
#endif

#ifndef SENSOR_H
#define SENSOR_H
//abstract class Sensor
class Sensor {
    public:
        //initialize the sensor
        inline virtual void begin(){ /*nothing*/ }; 
        //read function must be implemented
        //this is called a pure virtual function
        virtual int read() = 0; 
};
#endif

Now, you can create a TemperatureSensor like this:

#ifndef TEMPERATURESENSOR_H
#define TEMPERATURESENSOR_H
#include <WProgram.h>
//include classes Sensor and Debuggable
#include "Sensor.h"
#include "Debuggable.h"
class TemperatureSensor : public Sensor, public Debuggable {
    public:
        inline TemperatureSensor( byte userPin ) { 
            pin = userPin; 
        }
        //read function must be implemented
        virtual int read(); 
    private:
        byte pin;
};

//avarage a temperature and return the avaraged sum
int TemperatureSensor::read(){
    //TODO - implement arithmetic so that we return a degree celcius/farenheit
    float sum = analogRead(pin);
    for (byte i=0; i<10; i++){
        sum = analogRead(pin);
    }
    return (int)(.5 + sum / 10.);
}
#endif

And later, you could add a LightSensor like this:

#ifndef LIGHTSENSOR_H
#define LIGHTSENSOR_H
#include <WProgram.h>
//include classes Sensor and Debuggable
#include "Sensor.h"
#include "Debuggable.h"
class LightSensor : public Sensor, public Debuggable {
    public:
        inline LightSensor( byte userPin ) { 
            pin = userPin; 
        }
        //read function must be implemented
        virtual int read(); 
    private:
        byte pin;
};

int LightSensor::read(){
    //TODO - map( analogRead , 0 , 1024 , min , max );
    return analogRead(pin);
}
#endif


Why do we use hierarchy?

We use hierarchy in order to provide a way to make our code more divided.


How to make an inherited class?

This section will walk you through all the steps of making an inherited class from idea to result.

Define wanted functionality

The first thing you will need to do is to define what you want to add to the base class. This could be done in a series of ways but I suggest starting with a list of desired functions and a short description of what they should do.

	boolean begin();
		return true if device has been initialized successfully
		initializes the target device
	boolean available();
		return true if device is avalable, false if not.
		it should not try to poll device if no connection is  already established 

Familiarize with the superclass

You will need to know what data and functions you'll inherit, and thus being able to use. It will be a timesaver to either memorize the functions, or to have the headerfile easily accessible.

Learn c++ hierarchy syntax

Header Example

  1. #ifndef MYINHERITEDCLASS_H
  2. #define MYINHERITEDCLASS_H
  3.  
  4. #include "MyClass.h"
  5.  
  6. class MyInheritedClass : public MyClass {
  7. public:
  8.     void myClassFunction();
  9. };
  10.  
  11. #endif

'Code Analysis:'

  • Lines 1 and 2 are referred to as an include guard
    It basically prevents the code to get included into the program binary multiple times.
  • Line 4 includes MyClass
  • Line 6 is the beginning of the class itself. The ' : public MyClass' indicates inheritance. MyInheritedClass extends MyClass.
  • Line 7 uses the public keyword
  • Line 8 declares the function 'void myClassFunction();'
  • Line 9 is the end of the class.
  • Line 11 ends the #ifndef preprocessor directive

Implementation

First have a look at this: Basic Library Implementation

Debugging

First have a look at this: Basic Library Implementation

Example implementation

I will extend the Button library and make a Switch library. The switch library will need both a press and a release in order to change state. It's task is to transform a momentary switch (button) to a on-off pushbutton using software logic.

Define wanted functionality

add update()
add isOn()
add isOff()

Base class study

Public datas and functions

  1. #define PULLUP HIGH
  2. #define PULLDOWN LOW
  3. Button(uint8_t switchPin, uint8_t switchMode=PULLDOWN);
  4. void pullup();
  5. void pulldown();
  6. bool isPressed();

Create inherited class

//Under Construction

Usage of inherited class

//Under Construction


Links


Information about this page

Part of AlphaBeta Tutorials.
Last Modified: January 29, 2017, at 03:08 PM
By: Bachar Wehbi