EDIT
The title was previously: 'Using 'this' in an array of function pointers in a class', title changed to match what I really wanted to know, see reply #75.
I have previously used 'switch' to select a particular function based on an index. One example would be a menu system where pressing a button changes the value of a variable that indexes the menu, and then calls a function that does what is needed for that menu option. Using 'switch' works well, but I recently learned to use an array of function pointers to do the same thing. I think using function pointers is better because an array looks so much tidier than lots of nested 'switch' statements, and I can arrange the array how I like to be easy for me to read.
As I am also trying to understand how to use classes I naturally wanted to use function pointers in a class. I can do this having learned that this can only be done if the functions pointed to are static. While no an issue for my current use I can see that it is a bit of a bodge to be forced to use static functions because of they way they are being called, and I can see this could cause problems in some situations. From what I have managed to learn I think using 'this' in an array would do what I want, but I can't find how to do so. Maybe there's another solution as well that I'm not aware of.
Here is some sample code to illustrate what I can do, and what I am trying to do.
First, the desired output from the code is:
18:48:20.229 -> C:\Users\Perry Bebbington\Documents\Projects\UPS\UPS V2\Arduino\Test code\Function_Pointers_in_class\CPPfile.cpp
18:48:20.694 -> This is function zero
18:48:21.207 -> This is function one
18:48:21.718 -> This is function two
18:48:22.189 -> This is function zero
18:48:22.708 -> This is function one
18:48:23.223 -> This is function two
etc....
Using function pointers in a class, the following code generates the desired output:
Function_Pointers_in_class.ino
#include "HeaderFile.h"
SomeClass thisClass;
void setup() {
thisClass.startup(115200);
}
void loop() {
thisClass.bigFunction();
}
HeaderFile.h
#ifndef headerFile
#define headerFile
class SomeClass {
private:
static void littleFunctionZero(); // Functions need to be static for function pointers to work.
static void littleFunctionOne();
static void littleFunctionTwo();
public:
void startup(uint32_t baudRate = 9600);
void bigFunction();
};
#endif
CPPfile.cpp
#include "Arduino.h"
#include "HeaderFile.h"
void SomeClass::startup(uint32_t baudRate){
Serial.begin(baudRate);
char fileName[] = {__FILE__};
Serial.println(fileName);
}
void SomeClass::bigFunction() {
uint32_t currentMillis = millis();
static uint32_t lastMillis = 0;
static uint32_t wait = 500;
static uint8_t index = 0;
typedef void (*functionPtrs) (void);
functionPtrs someActions[3] = {
&littleFunctionZero, &littleFunctionOne, &littleFunctionTwo
};
if (currentMillis - lastMillis >= wait) {
lastMillis = currentMillis;
if(someActions[index]) {
someActions[index]();
index = ++index %3;
}
}
};
void SomeClass::littleFunctionZero() {
Serial.println("This is function zero");
}
void SomeClass::littleFunctionOne() {
Serial.println("This is function one");
}
void SomeClass::littleFunctionTwo() {
Serial.println("This is function two");
}
What I would like to do is replace:
typedef void (*functionPtrs) (void);
functionPtrs someActions[3] = {
&littleFunctionZero, &littleFunctionOne, &littleFunctionTwo
};
if (currentMillis - lastMillis >= wait) {
lastMillis = currentMillis;
if(someActions[index]) {
someActions[index]();
index = ++index %3;
}
}
With something that does not require the functions pointed to to be static. I think it should be possible to use 'this ->' in an array in a similar way, but I can't get it to compile. From what I have read 'this' has the type className*, so in the case of the example code above I think 'this' has the type SomeClass*. Based on this I tried:
SomeClass* somePointers[3] = {this -> littleFunctionZero, this -> littleFunctionOne, littleFunctionTwo};
With the functions still static the compiler error is:
cannot convert 'void (*)()' to 'SomeClass*' in initialization
With the functions not static the compiler error is:
cannot convert 'SomeClass::littleFunctionZero' from type 'void (SomeClass::)()' to type 'SomeClass*'
I've tried a few other things, but I don't see much point in listing them all.
I'm looking for either the correct way to do this or an alternative that achieves the same thing.
Thank you
