I am trying to write a library for encoders.
main.ino:
#include <./Encoders.h>
Encoders encoders();
void setup(){
Serial.begin(9600);
}
void loop(){
Serial.print("");
}
Encoders.h:
#ifndef Encoders_h
#define Encoders_h
#include "Arduino.h"
class Encoders{
public:
Encoders();
void EncodersSetup();
long RightCount;
long LeftCount;
void R_A_RISE();
void R_A_FALL();
void R_B_RISE();
void R_B_FALL();
void L_A_RISE();
void L_A_FALL();
void L_B_RISE();
void L_B_FALL();
private:
short R_A_SIG, R_B_SIG, L_A_SIG, L_B_SIG;
};
#endif
Encoders.cpp
#include "Arduino.h"
#include "Encoders.h"
long RightCount;
long LeftCount;
long R_A_SIG, R_B_SIG, L_A_SIG, L_B_SIG;
Encoders::Encoders(){
attachInterrupt(0, R_A_RISE, RISING);
attachInterrupt(1, R_B_RISE, RISING);
attachInterrupt(2, L_A_RISE, RISING);
attachInterrupt(3, L_B_RISE, RISING);
R_A_RISE();
}
void Encoders::R_A_RISE(){
detachInterrupt(0);
R_A_SIG = 1;
if(R_B_SIG == 0){
RightCount++;
}
if(R_B_SIG == 1){
RightCount--;
}
attachInterrupt(0, R_A_FALL, FALLING);
}
void Encoders::R_A_FALL(){
detachInterrupt(0);
R_A_SIG = 0;
if(R_B_SIG == 1){
RightCount++;
}
if(R_B_SIG == 0){
RightCount--;
}
attachInterrupt(0, R_A_RISE, RISING);
}
void Encoders::R_B_RISE(){
detachInterrupt(1);
R_B_SIG = 1;
if(R_A_SIG == 1){
RightCount++;
}
if(R_A_SIG == 0){
RightCount--;
}
attachInterrupt(1, R_B_FALL, FALLING);
}
void Encoders::R_B_FALL(){
detachInterrupt(1);
R_B_SIG = 0;
if(R_A_SIG == 0){
RightCount++;
}
if(R_A_SIG == 1){
RightCount--;
}
attachInterrupt(1, R_B_RISE, RISING);
}
void Encoders::L_A_RISE(){
detachInterrupt(2);
L_A_SIG = 1;
if(L_B_SIG == 0){
LeftCount++;
}
if(L_B_SIG == 1){
LeftCount--;
}
attachInterrupt(2, L_A_FALL, FALLING);
}
void Encoders::L_A_FALL(){
detachInterrupt(2);
L_A_SIG = 0;
if(L_B_SIG == 1){
LeftCount++;
}
if(L_B_SIG == 0){
LeftCount--;
}
attachInterrupt(2, L_A_RISE, RISING);
}
void Encoders::L_B_RISE(){
detachInterrupt(3);
L_B_SIG = 1;
if(L_A_SIG == 1){
LeftCount++;
}
if(L_A_SIG == 0){
LeftCount--;
}
attachInterrupt(3, L_B_FALL, FALLING);
}
void Encoders::L_B_FALL(){
detachInterrupt(3);
L_B_SIG = 0;
if(L_A_SIG == 0){
LeftCount++;
}
if(L_A_SIG == 1){
LeftCount--;
}
attachInterrupt(3, L_B_RISE, RISING);
}
When I try to compile this, I get errors like this:
C:/Users/marcel/Documents/dev/Arduino/encodeurs/Encoders.cpp:10:38: error: cannot convert 'Encoders::R_B_RISE' from type 'void (Encoders::)()' to type 'void (*)()'
I tried answers on other threads. Most said to make the functions passed to attachInterrupt()
static
. That threw different errors:
C:/Users/marcel/Documents/dev/Arduino/encodeurs/Encoders.cpp:16:33: error: cannot declare member function 'void Encoders::R_A_RISE()' to have static linkage [-fpermissive]
I also tried this:
attachInterrupt(0, &Encoders::R_A_RISE, this, RISING);
with no success.
The Arduino in question is a Mega but I doubt that matters.
Edit: Per Nick Gammon's answer, I now have this.
MotorEncoderMaster.ino
#include </home/marcel/dev/Arduino/encoders/MotorEncoderMaster/Encoders.h>
Encoders * Encoders::instances [2] = { NULL, NULL };
// instances of our class
Encoders right;
Encoders left;
void setup (){
right.begin (2); // pin D2
left.begin (3); // pin D3
} // end of setup
void loop (){
// whatever
} // end of loop
Encoders.h:
class Encoders{
volatile bool switchChanged;
static Encoders * instances [2];
static void switchPressedExt0(){
if(Encoders::instances [0] != NULL){
Encoders::instances [0]->switchPressed();
}
}
static void switchPressedExt1 (){
if (Encoders::instances [1] != NULL){
Encoders::instances [1]->switchPressed();
}
}
public:
void begin (const int whichPin){
pinMode (whichPin, INPUT_PULLUP);
switch (whichPin){
case 2:
attachInterrupt(0, switchPressedExt0, CHANGE);
instances [0] = this;
break;
case 3:
attachInterrupt(1, switchPressedExt1, CHANGE);
instances [1] = this;
break;
}
}
void switchPressed(){
switchChanged = true;
}
};
When I try to compile this, I get :
In file included from MotorEncoderMaster.ino:1:0:
/home/marcel/dev/Arduino/encoders/Encoders.h: In static member function ‘static void Encoders::switchPressedExt0()’:
/home/marcel/dev/Arduino/encoders/Encoders.h:7:34: error: ‘NULL’ was not declared in this scope
if(Encoders::instances [0] != NULL){
^
/home/marcel/dev/Arduino/encoders/Encoders.h: In static member function ‘static void Encoders::switchPressedExt1()’:
/home/marcel/dev/Arduino/encoders/Encoders.h:13:35: error: ‘NULL’ was not declared in this scope
if (Encoders::instances [1] != NULL){
^
/home/marcel/dev/Arduino/encoders/Encoders.h: In member function ‘void Encoders::begin(int)’:
/home/marcel/dev/Arduino/encoders/Encoders.h:21:24: error: ‘INPUT_PULLUP’ was not declared in this scope
pinMode (whichPin, INPUT_PULLUP);
^
/home/marcel/dev/Arduino/encoders/Encoders.h:21:36: error: ‘pinMode’ was not declared in this scope
pinMode (whichPin, INPUT_PULLUP);
^
/home/marcel/dev/Arduino/encoders/Encoders.h:24:45: error: ‘CHANGE’ was not declared in this scope
attachInterrupt(0, switchPressedExt0, CHANGE);
^
/home/marcel/dev/Arduino/encoders/Encoders.h:24:51: error: ‘attachInterrupt’ was not declared in this scope
attachInterrupt(0, switchPressedExt0, CHANGE);
^