Arduino Mega unable to read encoder fast enough

I have an Arduino Mega 2560 reading a Relative Non-contact Magnetic Shaft Encoder from Renishaw and I have successfully been able to read the position using the Arduino and printing to the serial monitor, but I have noticed that when moving quickly, it doesn’t return the correct value that it should return. For example, if I move it quickly 45 degrees right and then quickly 45 degrees back to the original position, it returns a different value.

 Code|
/*Slave Rotary MK8*/
#include <Wire.h>

/*Rotary Encoder*/
int encoderPhaseA = 3;
int encoderPhaseB = 4;
int encoderPreviousPhase = LOW;
int phaseComparison = LOW;

int a = 0, b = 1, c = 2, d = 3, e = 4, f = 5, g = 6, h = 7, i = 8, j = 9;

/*
byte part1 = 0;
byte part2 = 0;

byte one = 0;
byte two = 0;
*/
/*INITIALIZE VARIABLES FOR TRANSMISSION*/
int distanceTraveled = 0;

void setup() {
  Serial.begin(9600);
  pinMode (encoderPhaseA, INPUT);
  pinMode (encoderPhaseB, INPUT);

  Wire.begin(9);                // join i2c bus with address #8


}

void loop() {
  phaseComparison = digitalRead(encoderPhaseA);
  if ((encoderPreviousPhase == LOW) && (phaseComparison == HIGH)) {
    if (digitalRead(encoderPhaseB) == LOW) {
      distanceTraveled--;
    } else {
      distanceTraveled++;
    }

  }
  encoderPreviousPhase = phaseComparison;

  Serial.print (distanceTraveled);
  Serial.print ("/");
  Wire.onRequest(givePosition); // register event
}

// function that executes whenever data is requested by master
// this function is registered as an event, see setup()
void givePosition() {
  Wire.write((byte *)&distanceTraveled, sizeof(unsigned int));
  Serial.println("Position was sent");
}

It may be that the serial print is happening during the movement of the encoder. This will be slow at 9600 baud.

The read of the encoder will miss some pulses.

Try increasing the baud rate to a lot higher.

Weedpharma

windu34:
I have an Arduino Mega 2560 reading a Relative Non-contact Magnetic Shaft Encoder from Renishaw and I have successfully been able to read the position using the Arduino and printing to the serial monitor, but I have noticed that when moving quickly, it doesn’t return the correct value that it should return. For example, if I move it quickly 45 degrees right and then quickly 45 degrees back to the original position, it returns a different value.

 Code|

/Slave Rotary MK8/
#include <Wire.h>

/Rotary Encoder/
int encoderPhaseA = 3;
int encoderPhaseB = 4;
int encoderPreviousPhase = LOW;
int phaseComparison = LOW;

int a = 0, b = 1, c = 2, d = 3, e = 4, f = 5, g = 6, h = 7, i = 8, j = 9;

/*
byte part1 = 0;
byte part2 = 0;

byte one = 0;
byte two = 0;
*/
/INITIALIZE VARIABLES FOR TRANSMISSION/
int distanceTraveled = 0;

void setup() {
  Serial.begin(9600);
  pinMode (encoderPhaseA, INPUT);
  pinMode (encoderPhaseB, INPUT);

Wire.begin(9);                // join i2c bus with address #8

}

void loop() {
  phaseComparison = digitalRead(encoderPhaseA);
  if ((encoderPreviousPhase == LOW) && (phaseComparison == HIGH)) {
    if (digitalRead(encoderPhaseB) == LOW) {
      distanceTraveled–;
    } else {
      distanceTraveled++;
    }

}
  encoderPreviousPhase = phaseComparison;

Serial.print (distanceTraveled);
  Serial.print ("/");
  Wire.onRequest(givePosition); // register event
}

// function that executes whenever data is requested by master
// this function is registered as an event, see setup()
void givePosition() {
  Wire.write((byte *)&distanceTraveled, sizeof(unsigned int));
  Serial.println(“Position was sent”);
}

I would recommend you use interrupts instead of polling the stats, your are missing transitions.

Chuck.